pax_global_header00006660000000000000000000000064132320753010014506gustar00rootroot0000000000000052 comment=e1207cd81a418ae0bae7fd9476e41c2ccbdd4bd8 iptux-0.7.4/000077500000000000000000000000001323207530100126675ustar00rootroot00000000000000iptux-0.7.4/.editorconfig000066400000000000000000000004041323207530100153420ustar00rootroot00000000000000# top-most EditorConfig file root = true # Unix-style newlines with a newline ending every file [*] end_of_line = lf insert_final_newline = true trim_trailing_whitespace = true indent_style = space indent_size = 4 charset = utf-8 [*.{h,cpp}] indent_size = 2 iptux-0.7.4/.gitignore000066400000000000000000000024171323207530100146630ustar00rootroot00000000000000# # NOTE! Don't add files that are generated in specific # subdirectories here. Add them in the ".gitignore" file # in that subdirectory instead. # # NOTE! Please use 'git ls-files -i --exclude-standard' # command after changing this file, to see if there are # any tracked files which get ignored after the change. # # Normal rules # .* *.o *.o.* *.a *.s *.ko *.so *.so.dbg *.mod.c *.i *.lst *.symtypes *.order modules.builtin *.elf *.bin *.gz *.bz2 *.lzma *.gcno # # Top-level generic files # /tags /TAGS /linux /vmlinux /vmlinuz /System.map /Module.markers /Module.symvers # # git files that we don't want to ignore even it they are dot-files # !.gitignore !.mailmap # # Generated include files # include/config include/linux/version.h include/generated # stgit generated dirs patches-* # cscope files cscope.* ncscope.* # gnu global files GPATH GRTAGS GSYMS GTAGS *.orig *~ \#*# Makefile config.h config.log config.status po/POTFILES src/main/iptux stamp-h1 autom4te.cache *.gmo *.mo po/Makefile.in cmake_install.cmake CMakeCache.txt CMakeFiles install_manifest.txt build test/googletest-prefix CTestTestfile.cmake src/googletest-download/CMakeLists.txt src/googletest-download/googletest-prefix src/googletest-src src/Test src/Testing Testing src/iptux/libiptux_test *.cbp iptux-0.7.4/.travis.yml000066400000000000000000000010701323207530100147760ustar00rootroot00000000000000language: cpp cache: directories: - $HOME/Library/Caches/Homebrew os: - linux - osx compiler: - gcc - clang script: - '[ "$TRAVIS_OS_NAME" != osx ] || { mkdir build && cd build && cmake .. && make && make test; }' - '[ "$TRAVIS_OS_NAME" != linux ] || docker run -t -v `pwd`:/ws ubuntu:16.04 /ws/scripts/build_in_docker_ubuntu1604.sh' dist: trusty sudo: false install: - '[ "$TRAVIS_OS_NAME" != osx ] || brew update' - '[ "$TRAVIS_OS_NAME" != osx ] || brew install gettext gtk+ jsoncpp' matrix: fast_finish: true allow_failures: - os: osx iptux-0.7.4/CMakeLists.txt000066400000000000000000000017211323207530100154300ustar00rootroot00000000000000cmake_minimum_required (VERSION 3.1) project (iptux VERSION 0.7.4) set (CMAKE_CXX_STANDARD 11) if (APPLE AND EXISTS /usr/local/opt/gettext) list(APPEND CMAKE_PREFIX_PATH "/usr/local/opt/gettext") set(CMAKE_EXE_LINKER_FLAGS "-L/usr/local/opt/gettext/lib") endif() include(GNUInstallDirs) include(FindPkgConfig) include(FindGettext) include(FindIntl) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -O2") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -O2") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DGTK_DISABLE_SINGLE_INCLUDES -DGDK_DISABLE_DEPRECATED -DGTK_DISABLE_DEPRECATED -DGSEAL_ENABLE") if(NOT Intl_FOUND) message(FATAL_ERROR "libintl not found") endif(NOT Intl_FOUND) pkg_check_modules(GST gstreamer-1.0>=1.0) configure_file ( "${PROJECT_SOURCE_DIR}/src/iptux/config.h.in" "${PROJECT_BINARY_DIR}/src/iptux/config.h" ) enable_testing() add_subdirectory(src) add_subdirectory(po) add_subdirectory(pixmaps) add_subdirectory(sound) add_subdirectory(desktop) iptux-0.7.4/ChangeLog000066400000000000000000000062241323207530100144450ustar00rootroot000000000000002011-12-24 改进了如下问题 -资源文件不存在是程序异常退出 -广播网段过大时,启动时界面不响应 -正在文件传输过程中终止文件传输时程序异常退出 -在没有任务栏的系统中点主窗口的X按钮后主窗口无法调出 -与windows版,adroid版信鸽发送单个文件时对方不能接收 -往adroid版信鸽发多个文件时对方不能接收 -改进了接收文件夹时的协议,与原版飞鸽一致,接收与发送时加入了文件时间信息(飞鸽类软件都有这一项),改正了接收文件夹时的一个逻辑错误(这个错误会导致文件已经接收完,但是还不断去tcp连接中读取数据,这样界面上一直会显示没有正常结束) 2010-06-19 - issue 71: iptux crash when shared dir does not exist. 2009-10-07 -在alick的帮助下完成翻译修正工作 2009-10-02 -完成底层代码的大量整改工作 2009-07-11 -图片资源改由GTK+帮助管理 2009-04-16 -底层代码的少量修改 2009-03-09 -修正选择自定义声音路径无效的问题 2009-02-26 -文件已存在时自动重命令文件以防覆盖 -加入音量控制功能 2009-02-21 -实现面板上的来消息提示 2009-02-20 -完成反安装程序 2009-02-19 -更人性化的文件保存路径选择 2009-02-18 -完美处理文件的拖拽操作 2009-02-17 -加入声音提示、日志记录功能 2009-02-16 -完成声音模块 -添加从群发界面直接跳入单好友聊天模式功能 -为共享文件设置密码保护 2009-02-14 -取消背景变更 -更换程序logo 2009-02-13 -修正strpbrk()函数引发的编译出错 2009-02-09 -修正自定义头像不能被正确显示的错误 -实现文字与图像同步传输 2009-02-07 -取消友元类编码方法 -为某些命令增设标志位,用于识别更多种情形 -分离部分底层与界面代码 2009-01-14 -修正初始化丢失引发的段错误 -采用一套可选择的方案解决运行效率太低的问题 2009-01-12 -重新调整底层架构 2009-01-09 -解决缓冲区太小引发的诸多问题 2008-12-26 -使用Enter键直接发送消息 -组功能支持 2008-12-25 -新增网段描述表功能 2008-12-23 -新增64位大文件处理能力 2008-12-22 -增加排序功能 -调整配置文件存放路径 2008-12-21 -端口绑定出错则程序强制退出 2008-12-19 -修正端口绑定出错 2008-12-15 -最后一次处理图片传输,但是无法完成 -取消IP段自动添加功能 2008-12-13 -更新协议文档 2008-12-12 -完成形象照片传输,同时也为传输图片打好了基础 2008-12-11 -搞定个性签名 2008-12-10 -修正接收UDP数据时,缓冲区可能存在的溢出问题 -利用兼容特性减少网络数据发送量 -重制界面 2008-12-07 -更多错误提示 -修正遍历文件链表时释放内存出错 2008-12-05 -新增搜索功能 2008-12-03 -修正文件发送、接收兼容问题 2008-11-25 -修正接收文件时发生的内存泄漏 2008-11-22 -改善配置文件的读取与存储 -修正群发消息时的内存泄漏 2008-11-19 -修正与飞秋(FeiQ)之间的兼容性 -修正自动回复失效的错误 -修正不能接收文件的错误 iptux-0.7.4/LICENSE000066400000000000000000000432541323207530100137040ustar00rootroot00000000000000 GNU GENERAL PUBLIC LICENSE Version 2, June 1991 Copyright (C) 1989, 1991 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This General Public License applies to most of the Free Software Foundation's software and to any other program whose authors commit to using it. (Some other Free Software Foundation software is covered by the GNU Lesser General Public License instead.) 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 this service 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 make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights. These restrictions translate to certain responsibilities for you if you distribute copies of the software, or if you modify it. For example, if you distribute copies of such a program, whether gratis or for a fee, you must give the recipients all the rights that you have. 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. We protect your rights with two steps: (1) copyright the software, and (2) offer you this license which gives you legal permission to copy, distribute and/or modify the software. Also, for each author's protection and ours, we want to make certain that everyone understands that there is no warranty for this free software. If the software is modified by someone else and passed on, we want its recipients to know that what they have is not the original, so that any problems introduced by others will not reflect on the original authors' reputations. Finally, any free program is threatened constantly by software patents. We wish to avoid the danger that redistributors of a free program will individually obtain patent licenses, in effect making the program proprietary. To prevent this, we have made it clear that any patent must be licensed for everyone's free use or not licensed at all. The precise terms and conditions for copying, distribution and modification follow. GNU GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License applies to any program or other work which contains a notice placed by the copyright holder saying it may be distributed under the terms of this General Public License. The "Program", below, refers to any such program or work, and a "work based on the Program" means either the Program or any derivative work under copyright law: that is to say, a work containing the Program or a portion of it, either verbatim or with modifications and/or translated into another language. (Hereinafter, translation is included without limitation in the term "modification".) Each licensee is addressed as "you". Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running the Program is not restricted, and the output from the Program is covered only if its contents constitute a work based on the Program (independent of having been made by running the Program). Whether that is true depends on what the Program does. 1. You may copy and distribute 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 and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and give any other recipients of the Program a copy of this License along with the Program. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Program or any portion of it, thus forming a work based on the Program, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) You must cause the modified files to carry prominent notices stating that you changed the files and the date of any change. b) You must cause any work that you distribute or publish, that in whole or in part contains or is derived from the Program or any part thereof, to be licensed as a whole at no charge to all third parties under the terms of this License. c) If the modified program normally reads commands interactively when run, you must cause it, when started running for such interactive use in the most ordinary way, to print or display an announcement including an appropriate copyright notice and a notice that there is no warranty (or else, saying that you provide a warranty) and that users may redistribute the program under these conditions, and telling the user how to view a copy of this License. (Exception: if the Program itself is interactive but does not normally print such an announcement, your work based on the Program is not required to print an announcement.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Program, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Program, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Program. In addition, mere aggregation of another work not based on the Program with the Program (or with a work based on the Program) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may copy and distribute the Program (or a work based on it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you also do one of the following: a) Accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, b) Accompany it with a written offer, valid for at least three years, to give any third party, for a charge no more than your cost of physically performing source distribution, a complete machine-readable copy of the corresponding source code, to be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, c) Accompany it with the information you received as to the offer to distribute corresponding source code. (This alternative is allowed only for noncommercial distribution and only if you received the program in object code or executable form with such an offer, in accord with Subsection b above.) The source code for a work means the preferred form of the work for making modifications to it. For an executable work, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the executable. However, as a special exception, the source code distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. If distribution of executable or object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place counts as distribution of the source code, even though third parties are not compelled to copy the source along with the object code. 4. You may not copy, modify, sublicense, or distribute the Program except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense or distribute the Program is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 5. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Program or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Program (or any work based on the Program), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Program or works based on it. 6. Each time you redistribute the Program (or any work based on the Program), the recipient automatically receives a license from the original licensor to copy, distribute or modify the Program subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties to this License. 7. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), 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 distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Program at all. For example, if a patent license would not permit royalty-free redistribution of the Program by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Program. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system, which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 8. If the distribution and/or use of the Program is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Program under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 9. The Free Software Foundation may publish revised and/or new versions of the 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 a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of this License, you may choose any version ever published by the Free Software Foundation. 10. If you wish to incorporate parts of the Program into other free programs whose distribution conditions are different, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, 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. 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE 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. 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 convey 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 2 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, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. Also add information on how to contact you by electronic and paper mail. If the program is interactive, make it output a short notice like this when it starts in an interactive mode: Gnomovision version 69, Copyright (C) year name of author Gnomovision 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, the commands you use may be called something other than `show w' and `show c'; they could even be mouse-clicks or menu items--whatever suits your program. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the program, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the program `Gnomovision' (which makes passes at compilers) written by James Hacker. , 1 April 1989 Ty Coon, President of Vice This 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. iptux-0.7.4/NEWS.md000066400000000000000000000077611323207530100140000ustar00rootroot00000000000000# 0.7.4 (2018-01-24) * [#?] fix bug in save share management. * [#97] don't download googletest if already installed. # 0.7.3 (2018-01-20) * [#98] fix typo, thanks to @hosiet. * [#100] fix crash on the context menu of statusicon. # 0.7.2 (2018-01-16) * [?] fix crash when clicking on the popup menu of the mainwindow. * [?] introduce gtest. * [?] support specify config from command line. * [#92] clean the icon namespace. * [?] update po/iptux.pot, update `zh_CN` translation. # 0.7.1 (2018-01-14) * [?] fix build guide in `README.md` and homebrew. * [#80] honor the default `CMAKE_C_FLAGS` and `CMAKE_CXX_FLAGS`, thanks to @hosiet. * [#81] fix crash on status icon click. # 0.7.0 (2018-01-10) * [#33] refactor src/AnalogFS.cpp to make the bug log has more information. * [#61] switch from autotools to cmake. * [#67] improve compile under MacOS, thanks to @jiegec. * [#70] switch config system from gconf to jsoncpp1. * [#74] fix critial warning on peer window. # 0.6.4 (2017-08-22) * [#58] fix compile problem under gcc 7. # 0.6.3 (2015-09-29) * [#44] Add "Keywords" entries to iptux.desktop, etc. * [#43] Remove deprecated "Encoding" in group "Desktop Entry". * [#45] Upgrade to GStreamer from 0.10 to 1.0. # 0.6.2 (2014-02-06) * [#26] iptux --version should work without DISPLAY env. * [#28] code.google.com -> github.com # 0.6.1 (2013-12-14) * [#20] fix compile problem under MacOSX 10.9 # 0.6.0 (2013-06-05) * [#8] fix autoreconf warning * [#6] add travis support * [#4] buildable under Linux * [#1] buildable under Mac OSX # OLD RELEASES * 2012-2-29 把文件接收发送界面放在了聊天窗口内,根据此功能需要底层数据结构作相应改动 * 2011-12-24 改进了如下问题 1.资源文件不存在是程序异常退出 2.广播网段过大时,启动时界面不响应 3.正在文件传输过程中终止文件传输时程序异常退出 4.在没有任务栏的系统中点主窗口的X按钮后主窗口无法调出 5.与windows版,adroid版信鸽发送单个文件时对方不能接收 6.往adroid版信鸽发多个文件时对方不能接收 7.改进了接收文件夹时的协议,与原版飞鸽一致,接收与发送时加入了文件时间信息(飞鸽类软件都有这一项),改正了接收文件夹时的一个逻辑错误(这个错误会导致文件已经接收完,但是还不断去tcp连接中读取数据,这样界面上一直会显示没有正常结束) * 2009-11-20 源码包不能安装,更新 * 2009-11-19 修正已发现的致命错误,并更新源码包 * 2009-11-01 发布最新版iptux-0.5.1源码包 * 2009-10-10 貌似0.5.0这个版本中的问题很多啊,这几天我都在不停的改版本号。 * 2009-10-09 降低iptux对`Gtk+`高版本库的依赖,现在iptux需要的`Gtk+`库的最低版本为2.12.0,如果还低于此版本,那我只能表示很抱歉了。 * 2009-10-08 发布最新版iptux-0.5.0源码包。另,鉴于很多哥们的库版本比较低,所以这一次除了发布一个正规的版本(0.5.0)外,顺便也发布了一个对库文件要求较低的版本(0.5.0-lv),所以下载的时候请参考自己的实际情形选择下载。 * 2009-09-30 郁闷,有些人加入了项目之后都不做事,这算什么嘛?我决定清理成员了 * 2009-05-12 继续0.4.6版开发,加入聊天窗口中对http://等url的识别和链接功能 * 2009-03-09 鉴于0.4.5版中存在一个严重错误,所以建议尽快更新为0.4.5-1版 * 2009-03-02 发布最新iptux-0.4.5源码包 * 2009-01-17 发布最新iptux-0.4.4源码包 * 2008-12-31 新加入项目成员 pentie@gmail.com ,PT * 2008-12-24 发布iptux-0.4.3 .rpm包,由网友 liangsuilong 提供 * 2008-12-17 发布iptux-0.4.3 .deb及二进制包,由网友 mdjhu@sina.com 提供 * 2008-12-16 发布最新iptux-0.4.3源码包 * 2008-12-07 发布最新iptux-0.4.2相关包,二进制包由网友 mdjhu@sina.com 提供 * 2008-12-04 新上传三个二进制包,由网友 mdjhu@sina.com 提供 iptux-0.7.4/README.md000066400000000000000000000064621323207530100141560ustar00rootroot00000000000000 **Table of Contents** *generated with [DocToc](https://github.com/thlorenz/doctoc)* - [iptux: 飞鸽传书 GNU/Linux 版](#iptux-%E9%A3%9E%E9%B8%BD%E4%BC%A0%E4%B9%A6-gnulinux-%E7%89%88) - [Install](#install) - [Linux (Debian and Ubuntu)](#linux-debian-and-ubuntu) - [Mac OS X](#mac-os-x) - [Build from source](#build-from-source) - [Linux (Debian and Ubuntu)](#linux-debian-and-ubuntu-1) - [Mac OS X](#mac-os-x-1) - [贡献](#%E8%B4%A1%E7%8C%AE) - [声明](#%E5%A3%B0%E6%98%8E) - [基本](#%E5%9F%BA%E6%9C%AC) - [提高](#%E6%8F%90%E9%AB%98) - [相关](#%E7%9B%B8%E5%85%B3) - [必须](#%E5%BF%85%E9%A1%BB) - [TODO](#todo) - [How to update `po/iptux.pot`](#how-to-update-poiptuxpot) # iptux: 飞鸽传书 GNU/Linux 版 [![Build Status](https://travis-ci.org/iptux-src/iptux.png?branch=master)](https://travis-ci.org/iptux-src/iptux) [![GitHub version](https://badge.fury.io/gh/iptux-src%2Fiptux.png)](http://badge.fury.io/gh/iptux-src%2Fiptux) ## Install ### Linux (Debian and Ubuntu) ``` sudo apt-get install iptux ``` ### Mac OS X ``` brew install https://raw.githubusercontent.com/iptux-src/iptux/master/homebrew/iptux.rb ``` ## Build from source ### Linux (Debian and Ubuntu) * for Ubuntu 14.04, please download from https://github.com/iptux-src/iptux/releases/tag/v0.6.4 ``` sudo apt-get install git libgtk2.0-dev libglib2.0-dev libgstreamer1.0-dev libjsoncpp-dev g++ make cmake git clone git://github.com/iptux-src/iptux.git cd iptux mkdir build && cd build && cmake .. && make sudo make install iptux ``` ### Mac OS X ``` brew install gettext gtk+ cmake jsoncpp gstreamer git clone git://github.com/iptux-src/iptux.git cd iptux mkdir build && cd build && cmake .. && make sudo make install iptux ``` ## 贡献 * [Launchpad](http://translations.launchpad.net/iptux/trunk) 为 iptux 贡献翻译。页面由 LI Daobing <lidaobing@gmail.com> 提供; * 欢迎为 iptux (最新版) 制作二进制包、提供补丁。 ## 声明 请总是使用最新版本!! * 老版本中出现的 bug 可能已被修正; * 许多新特性需要您的试用。 ## 基本 兼容 Windows 版[飞鸽传书](http://www.ipmsg.org.cn/)、[飞秋](http://www.feiq18.com/)和 Android 版飞鸽协议,也兼容日本 SHIROUZU Hiroaki (白水啓章) 先生原著的 [IP Messenger](http://ipmsg.org/) 实现局域网的通信,文件传输。 ## 提高 自定义一部分命令字,实现文件共享功能,群组通信,自动识别编码 ## 相关 请查看 Wiki 标签,那里可能有你需要的内容! ## 必须 * 打开防火墙的 TCP/UDP 2425 端口 * 运行命令: `sudo gtk-update-icon-cache PREFIX/share/icons/hicolor` (使用时机: 图标显示异常,PREFIX 为程序安装目录) ## TODO 错误不可避免,请发送错误报告到 https://github.com/iptux-src/iptux/issues ## How to update `po/iptux.pot` ``` xgettext \ --output=po/iptux.pot \ --files-from=po/POTFILES.in \ --language=C++ \ --keyword=_ \ --from-code=utf-8 \ --package-name=iptux \ --msgid-bugs-address=https://github.com/iptux-src/iptux/issues/new \ --package-version=0.7.3 ``` iptux-0.7.4/desktop/000077500000000000000000000000001323207530100143405ustar00rootroot00000000000000iptux-0.7.4/desktop/CMakeLists.txt000066400000000000000000000002331323207530100170760ustar00rootroot00000000000000install(FILES iptux.desktop DESTINATION ${CMAKE_INSTALL_DATADIR}/applications ) install(DIRECTORY hicolor DESTINATION ${CMAKE_INSTALL_DATADIR}/icons ) iptux-0.7.4/desktop/hicolor/000077500000000000000000000000001323207530100157775ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/16x16/000077500000000000000000000000001323207530100165645ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/16x16/apps/000077500000000000000000000000001323207530100175275ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/16x16/apps/iptux-i.png000066400000000000000000000016361323207530100216420ustar00rootroot00000000000000PNG  IHDR醟sBIT|dUIDAT8mKh\usޙIIɔ$iVcZ" *U AEWnfQZ]R(-T4R[+&d4@[d&&f2d7s<gys9= GjK6G'CF e܌ڎKK&gHeЀz_%m:uToz[D"[ߗunO$2 "%q$gFVKrzLy}rQquR:Q΍O1Ȭu2?TJ}n6 \&Mfz$Xbka{hj庿IAa -uo*|2Bi^ ˠ,nMPc~8r=tவ-wX^RnqDPJGDy ׌Ki\.<2dYvDot*~J.yG]hPne B3LK)JJg1¿tߪ;c3Sϕ5&9!/R(9IQ%e+H>G̵諏 ё^Oor<]I("XFGcV?ս quky)4_GȬ$-CҶPL'͇'G;00P3XmzWݽPJ!VoI.wdcw?o58UTIENDB`iptux-0.7.4/desktop/hicolor/16x16/apps/iptux.png000066400000000000000000000017021323207530100214060ustar00rootroot00000000000000PNG  IHDR醟sBIT|dyIDAT8m]L[uQJ](oBns2 n1ۅ8KvA.(Co1+fYlb AE-y#?Ysѽi)(gm,޽tvv:fP^fT0RDcTJ}bW35z#>ٮ..NVDJO??gf9uF3c |r4Sp=u88p~ zGGRQOC5N.pk*U^AW5j8v}?VUkkkHvFIENDB`iptux-0.7.4/desktop/hicolor/22x22/000077500000000000000000000000001323207530100165565ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/22x22/apps/000077500000000000000000000000001323207530100175215ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/22x22/apps/iptux-i.png000066400000000000000000000027431323207530100216340ustar00rootroot00000000000000PNG  IHDR+EsBIT|dIDATHmlgszӳShVVK1hpd%ۇiqn"N7/Ѹiۺѭ9eN?Or|HSH^8[lTEh4jԋ/'dĢY+8]ܿa6U'q8\:T +޽驘Y[[YA&Ak8hA;  (-X!R?oSb=NdhlT,e6F7SM}y9p)䏯g{71=KJz%ɓMvê5LŒ8Z/\B .kk¬ sytqPZx4>A^ @,ʏ5d* ֥[@29VB^9Xk9}q%2 (~ZjA;"TiZFHSbA>DΧ1CRX ;"lkB,=?l GE,wToXE HK pAJZ"YYhQnѢE\@KƩmk3s|@K(TgC(b4 ;JB0}v]ft_=9w~G=1"(%9}5̜!o<^l! E1y).Yp]8kcձ }L2֒,9S Ύ&Hy5J+VOָZ3Y窿V`vb^сo~YX_|Cnf G"oH22VJ5)PjT 1吓yZ/֖((ɡ7_ߒ FPc-92k& q.r| zյǐR~d=!63h]NYv~R Wh1BSṡ/_>ߒH* C`Z$)pCTRT?rB*Jh%lJ˾tYk2bkRZ]Ih"-yNJtM>_$=M"܂Lah-oJ{|rZ=;+{#;6[lœlb$HY0 L)1Ĕ&i='} ߺ]/-ݿyOUU e0-imGff8sJ0͖ 'y~;>V+ZKKmϾ32ɜ lbJ)eJ>fkIc1 .]ۨNF<$i?3ՉɊ[fRHj۽Ŷmcȵ s~~ n7}~{{{:u ~)2+@V+#/ޖecVWWwSI !IENDB`iptux-0.7.4/desktop/hicolor/24x24/000077500000000000000000000000001323207530100165625ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/24x24/apps/000077500000000000000000000000001323207530100175255ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/24x24/apps/iptux-i.png000066400000000000000000000031771323207530100216420ustar00rootroot00000000000000PNG  IHDR4.sBIT|d6IDATHilTP]2!/i @8:Jhz%tO@O87wպ) !BZԛBJ|?g,0 g.\MLmXoںHWx}Q.*y:.gR}?G>B4@SBPX"\RN{7nA^dd?'gDDF7/ssKUN̦)3KLfbO!X[Ih; !B[DrJEH!DS S068pRk3=D]]]beBaIENDB`iptux-0.7.4/desktop/hicolor/24x24/apps/iptux.png000066400000000000000000000033741323207530100214130ustar00rootroot00000000000000PNG  IHDR4.sBIT|dIDATHilsk/ 0G)!#@)jEUR( -JJU5V"ڪ)"C#7dsp |cz}vmϗьfuq /ﯘJB"1h)u2;3رc׿(2iimsNˮ'ey++摕N`8JexM!ݣgԮXM6^+--5vᴮ7]QKra?X v-aE(jQ>,1N.#w֛o2W=kU6 lX#gY }CQ x\V󛝫a"v?SNn˟1{Fk>`8҄Bf7P__vAf^z3w۶BC㪅dMI!"\rRK qҒ|.[,BfuZ$:w9٧؛'0DkRhuVa(1()BWG8Oopԛs|;{p,B$D21yĊ?a|ZMg' EH7{:Ѥ i{愌&Gk#ܥ$XY0- K;LSh b9+_2UWWW״tn.()o`%F2ɪdxǍ, ۲1@|?b8$#̓?5sGu/x+yQ )@GqZ+LE/Ȣh"ݮD%g'Z! lLIua%'Ef޶bcNfbB䧫|LKO jb3h -ϙFI$Th>R"GJ v/0!>lUeE,($omyr !4UvN) x !HZ#B,KrҥPZQ:g:aAߨA`)*$w+DzزywKKeYnᣖ^lۢcO׃qSeRC)sF{I4n͏LgJRlßnte()YQKqffy)WwR FmMY]+=Pu".l*TdQwomBRԵ8pC2QZ#)Da{칦sAϝKaR98 0Cao'h rkm;XmY(q,=b?xЋ*r,=01"sN10hB2-,aF~vP555wm\'ou<-~ @6DlHf8ba%s ƣ Wi&8Xyu_ZŽ{ԏi7+gWT :`Pl8`Ac=4m9;oAvW?X}}555OvvU\Q=Ir֐>}L2ڵk`7ɯo n;G6v̚ih9"b!vb'͝;܈Fv]ws-l>ӒJϚǀEYTd"z00eBpOq#(IwG;<,5rQuuƍ/u&.;s4;A[g7nh ւ,;k_Da$Dc1<9k֬Y`ᆳ7_=aʘs롵~@ˤV'eϑt$Rl`nB;.G18G_ x[3g(?6ܬ4Z<:P2qx).GRJ'X hr%S+ʨoacn߰aC <d%[ŗ(jtr @)rRJVX4+2l0!G 9()+(R,o' m Lv-/~ZzYzt"[:HA*?8(A9 'Jc`a5iXR $z<.dDQX2W,/LMMMuhu%`ﱶb peʔsI=[IMÑ_%~gN9L`7DIB!ƖP1)[;H+n拖Niwy3̽l鴇O7;{ZWt-Ɍ(?B"Hk_XΪ ӝRr-ojB+>LPSI!S8tV8"AJѧrICbL5wꎟܠPH x?[`" E@( Av&xeQYT5d9('( NaP|yˣLPJ)uFXd" c`OJ(%7OoF!+6 "DeHR8cR V]8#KzqQ>j@9NOMryik? ACh<=|Ɔa X$ w8$uA=Y_ww٬Ol TQa?8+@fSԧ`aQ}PAHvFk3 5{DP/@rÔQ,{wD2i49<GV(o#(=/~+F y#S:/+.;@PLRd*˓{ɝK"badYvIu1X_>crneeMkglYk-AӤ=ñD4z(%C3 0㐊BH\!fd^}930\{]kx!Z\cPBXF#k9z*E .U`E+ֹ 3ncIHi1͠w=Ͽ;u=Ǖ?O`osAR ў .$2P# .ZJ)Pp_%߸9`7۽{;űm(W-R3@ "[ڭE8J2Xȝ[VnݺQV{uʷ?Pp̥ 28RڐX~ϳ$WXh!B #oWvʘk֬=$_3}+WG.9w*D,6_)c֒5ςg,1x&Z`h'_WM,++;+Ya;_*gK0Jak 祥=o]o7N=j+#~xҙ]G :6s5u\o"юFS/W)r2|[E̿i"yAZZx؅ж<3k[nCfL̡ -ضuѮƸL.2.ʒhm8s],ze|4?o /}w9ˁ̹g&cN=|g51@ D5>nOͽ{(^zղhc3x$<\^ @^ rgo 3wS]BeaYR&?j^ey7_U`;.ϾywRߺs'u`͛%Klj.s[~&"M%QJR KY(euX֗Fʤ)}e/mde` ywu2mذa񞳡GgG}sdTnњ%u" |@26QW"*~|_VΠeXjaPʀ ~njRh!"=QJ |bՍc ^Efh]cR`B+ڵkG ҲB'(d %Ы[ wH(n)5ql\!E AG(c dJJRBCL\]@$PZvhfl,2kph1k|E H1{xxv_浊T߲,@-|w\W;My˲d k 6XB,ɔ }Hk|opoO8u juΪ[l^p!,Zx}'L4m\Eor>NBnIC[Ҙ;"Tǘ\u%_]t霮o)G}Z4*{p!!h\cB ,eW !hDP$$=D5)cpo[Yf͚Z0cǎ6nx}vMj\c0u+Dc{WXh}_# |wzIENDB`iptux-0.7.4/desktop/hicolor/48x48/000077500000000000000000000000001323207530100165765ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/48x48/apps/000077500000000000000000000000001323207530100175415ustar00rootroot00000000000000iptux-0.7.4/desktop/hicolor/48x48/apps/iptux-i.png000066400000000000000000000106531323207530100216530ustar00rootroot00000000000000PNG  IHDR5-c#sBIT|dbIDAThyp՝?u%$IuXe#d6+mH'$H0KB[[e7 IR K*E6N 1GbmM-[uh9?gFl}U<{^ M۷ooشi^|A*t:UJQVZJu$BiI uns/իWكsA\]vk׮/=ÑpIUe}S@YUU̙LU$BQq`(4ضE21Nl4FO7'HǨ()&{;NZWP?OVڵ뮁ڒy-JyD"5B!XZc)eYh } t&cYGcҾo/S=]-_k=_z衇ks|ym|jj."K;<ʱaFSiIVˊUU,[HMY1%!Ҋ$xi:;/{~k3o$Õq(cr2Et4h8cؖJ)hZa0'fbQ#R^2gQ*+S__j=Ν;8 Ɩ7?lҫXxd'93aGLh= ! TJ32x}ͱSIME)ϤED@͡]]Z\3j~"6?Բ>]W^_<{R0 3@2ƶmAceMkOJϧ֤-d"m9sVn\flE4[^'~e55XzuOu2/KqW(ftt(vF)m|*0Fړ^o!y X>o6t H7`0[y-l`+hme"e'`p矼K;,fu[ TCTC̫ 8gl:F1qg9UTYFӊ;?rŝ;wveK>bJ-z\zaˢuCQS ` CJH@RJ ùO!`yl`1uiLCo}<>9'zx O0|_HI{Nl׮]? n;+:>:cUカ2LN3!43n\&kea:sGeJ)+ ":N_A"c,^%.joo#A=SzL5/Xt5XB244d"Y]ĆʲX}{ɴ2 Lk8x;>o*+?4w۶mkzwZ<֖+>##$IosB` 0NQ3ʂ={l2,D"ɻ1`LLIdbteCO>)(꿹u"5%G9vs|!b}47QʋN4ɌEl2EWtg9̷ɑAA.9sZ[3"mi3Pc.6wtt\w]wGştN#ɌM"7化F] NVyl9~GJ--BDF芎a )lAB8ϱۻX~oR2ûxG@=c 1Fٶ'G0r(w3) Kex{ Ik)%Je)PrF`=31&ߠ /8n}koF0H2cNqYP*lR4B`R4qFYϪW5RU$Hl=x2B!RB9K/NT.iׂ,[uV -J(0orrt,Uq"D&:(hvd%\%@"uLhm @}lm[|ݶE4uIy: B)'j. wFI`: z'ێt= F pʹW@04ib*ϏP7k,0BO+F_>0S{< ,c)~95zjU^P#A+3IeI1G_,h@-9t* D!ipz.l3lNkzbM7Cػl9,E80:o{GL3-N&R<{l11O tئI""b#XBb `2:wk,2ox x^;_[;,1'wV}lEWnpޚʲH6 $W# {w}xߎ͟{FpϽ/sYK+HG*I+!]8?nGEsS,(b<v8|S_'ۇƾ<Ԯ#tZc5-q}@Qpw"‘ǔkdc4mV~ǁqWvVo~7n8x^EI\gBZL֚\g'}I2~-V^v_ǛbԵݻwWlڴg)9DIB0ce]vs;VضڿʆӾS<}wt)`>q_eֻb(YR,O_e5"dxDVRX4DL铝<>n݋6l2Ae͛7>Ei柴 (W^YY,.)QeVL*;E&v 12,C覰]'~|PKKKwWF;vhy~e {ƻ0k:'8ͬ2jk T2w>7ڱ5kְ~%KK 6s'IENDB`iptux-0.7.4/desktop/hicolor/48x48/apps/iptux.png000066400000000000000000000113771323207530100214310ustar00rootroot00000000000000PNG  IHDR5-c#sBIT|dIDATh{tU՝?{s77@BDPJZ(3Z:3ڥծjj-.TZQbQ EI In޹y>{8$κ{o~\<֖<3Z@vHR477E)PI䄘^VF[kn_|y۝wyA VX;hhh',B\鹺4/(`ʴiL(,$%R !̩D{zHAotw}7ԋ/X][[v zzcZkR>RhsLabj*1q!cl367S}E/{ J|O L^FQ\RZh?d ۶JҨWJBiGJ&f{HYHCh fyW:+`՗fakJyۭny}nP۷o_[~m{krJ.맳g" %, Tmrl!e9]XΒeaH֚Eݙ^ gJyX8s2Y´R,72cz{_~?ӑFz޼ܒRzii릧+QqAٚO[+?|xao=AJ&a"Z8ϋ5[ a;|G:2 ߼y3K.]:0֍Jh;aZ+|:f|kH)(GhCkM_,>KP(.aGU3's՘eU5}!V:|05M*i!DJ0$!3Ga d|.k,.Dn/so_mGm l !:{6ene;T__?Q3iYkoG{hm颷>gBJ!R.yYLh`0R )E湞!xquZA ~Zyڵ|LPjuw\mz#?*`pI @,OOKp5EٱX"# x f\s#]xvܹΊv~Tdf菎.BA,cMgZkl-{lu}Jk:,WJ( f)lIW_ N3jhoߪl=J.?#Cu1:|ICk7R3R)w,¿o}&iyFx`%$mK*bf> }e3@ss7ʯܩIZC4a\Ҫpk QJ:31 ,/s-J]S$WP7=8:|1nf^$3Odaa-P>g\R2K`#\Ӏr>d=Dg/m1hce$|HZ: 1ή>: } P[[zxy] d$B $% >iK Np5USYS5,HY60m` t),6ִmQhZv-Nr?y {%~ANv|{Ji(4D pN@FAXL)5ʆRn_m "ipr1yLaÅ3c= I -^$k(,9Dk޼5vFܼ#R:VtF&R%i0!򍙬Ç2oh0%~R s˖-܂+,K-J(^; \Y<;F^ls2b-V 7D 3y%R,+/"bD>d3%7 ( FkMg,wc0$15l1αNbR PVZ>xL3/v\38iE*5"pGŘ+%Ma~QPR<Ǻ]sBHRb+5HrE:;LO&L(AL6١FE8)Z SH:㊦UIJ \bGZx$'ˤ(䧢 Ӌ6.BS=(;> X)}^fM,v SH)a6R%X]1 q. 5umi6yVWrdZzctx I\3g 1)v)X`:J , )J@4sgbZ QRdܠ\mW Y[QLgrZ}rS)+ˋ1 +3Dzcx9Seta^)[?9Nc[0BmdR:$r-Rt9/F9fB )]Ή 0MϙĔp֘q4lmh⓶>ed{Mۢ<]LǼ4N`FAY87"E/ CKs'p6`vv"[9}6Ӑe۸E upPD0$wUS: 5t1 _Ʉom?iaF;^/>(O2M:¡OOP6h9X7vC 2' Qo\59 cZV ڙET3sz I'' j*S|ɡ(2#J)I?JVvpwז 6|dLfL4ZP9>SǓew7׎CJWe(Blqk6um=.V\RC".DŽēCiPB Eۑx(o&8y/iK44SC>,&=i>h!/ ??i񓽍\UVH7̙D|/?<HIPh3t?zK~dɒsώܖ0N% S}H ՅZR0 nS̤P)[Ӷ>Nav~Ǡ/M]tV@h,D?P,T(ܪoU; LCuuu^2y,Щ ZPx !ڗR8vrLqy&]o*4Q ]ZPj FaM)+Z~555 FdZjK;^gN3aR[6qmݪvNwlIɀ0& /MA[,!Ʃ=y닃MkoXac63k.xkT+d3VKk Izig O A/IpI(Z0Uׯ[|16Y׭['~<`0 м#5'ur?XZckҊk(mD"xW.~k7=hѢ1A}ά.^NK~`w!e0 s` w\QirA^y믿)IN-Kg/*3ȸHP8`%IvDЭmjdZ=`^ջ˖-u] sJ[~ yէ  'cp>d="Ja!Aw ^q"owϙ3穿۶m+۵kW+[r]7 -hn&HY[e;!qy̫(}eVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/9%bKGD pHYs.#.#x?vtIME+۩7GIDATx͛{ՕǿVuσy0ga!2l.뢫YD&F&*$d6슉(#bbQ0 0WݻTuuWw`1ԧ;ZkRCݸwދ{y477'RJR|>&L@AA?^YYY2b_AAAq ̡C׮]nݺkkkkvXX4|La1%21 AYQho ph=?k9}lqGO^zrqܹ5kLo84wgOb4KGCsQƺ:jw͛+K e}z73gǎ0P˗O^||qE5N6W`PA>AD&Q#DQ O&>S;K86m`߲͊kz>'r`y˗/pѢEZY.uLJP?a'C]S+ M9HK{]PwP8Z3A/?a2e15!$ t]]k{g=]c,//òexGf!pF_5Z)Z;{h sX.(hR gC}#G cRPf|m4c $SN47?`Y…n lܸq*9{s!RК;ZmUxіw때)쇥4](= wC־f%\QJqw^U-<OEpGteY*6@iG {p&ߟ5nG`ſ{woZp|>^gجi  ϲ%m۶&2wl\~Z:a>WG'`{QJ%(frfQ0{Ͻs[ߓYpsVi]=ڻB:CvY|}ڮ]6|>y.lYrS߶eCEXZX0RJw)DH{c Oͮ:mP}c*>;e [^Œg_H[ҔHtyB ,;T3w_]N0- Iz|HzPR )E!R2?}dA|dpZZ:XB`)1MfS~_رci|M[~y,Bfd%!E}s$ba7 iJLao_}}sςDUV=/^K3p0Jk:z?$pһ J} >70޼`ؽ>YPYcҐy?QA͛7g|[c.]8}Q9Ќ bh2B !R txb} G@ާ<ڎKऺU8fH$oc'5+pyiYP P@TkgzI TLҧg`+ <+bU^ ߇Gg]A;´wW︺a'{/***:`&_G=рҚ7dMJ@!OTʾkHRl̹%)Gߠ+6vh}D=H[&i-"^vug_Ń3AA_f͚o<9x`!&;X RcNQZz&9A:q\?k*a{hdPua… ;O!'@}4adb#/eIH{PH&1cї )p( R1:hCN 6$ES.d˿ øfnހ%#60]$$%Rc\\V̱gP6 ;Ѥ#OC)ǫ9~L4M +!dfOںuk ?}ŵuG3q(?ҏ}Q)eJ!і3WY~GBBmecgoRG'3NXGYQzk|&ibf;|֭[-YY"9Ǖ& .9RSu)$vrOOnJYHI{#i2% @8A8whXrW6eg:aH@I#H`:j61tlluء\;nI)~G6b8#p"16%G8smY#'L,"^z饧g\ RyX #gԤ[n$|P>w^4!N.6}rP$m=MdD: @ 7~ddddkkkm& 2^c 0e58յ)^RJ 2x)d'oH t7v爹`/eD"8'x蛃aD@e3+7o~yª3Fh_D~y5 ZCd3-3}&?>,IAXG7=~@*:\Hp< QBڬ1$gfM$؅ZO:\{~&Cإj m҈s& {g)@O޶HdO";I Bc9d'&]ǏPVVܹs9!vFRX-B%R)Qƙl?|]<[fxŤWK%3f|:!X4f8Zh)l 52zu}4v" 3'5KA|k҈SZmws2vJ}{7%CXh"h`t|%%%p8OrP)RֶK\v+M? /MԳlñP8B]-SULj ?g, im(ʔS*9{3c3hE?^ge4IhW>o~o=CU9`.% T8V)P3G٣&)alȹ pj%AÎ(Zj88tjD1Ip*sJP tF+';R bRr& v,š_N0 @EnxR$$U:!Mզҁ\=rЩD-~V-띸! P7 +X*OV23Y9)-)?O6Ϛ5D zXlI?9HRJf1{li%W9¡n[вEoqb[2A` 7+_3fl8p`@w}qO>qj!(q9duͼQ}t!d Gy2)Ť3"#"(pԽaܹkݸSYY8,:N80z#ƦDp|wM.&42Pk(²]ݒC%iD@& A aK݆%(0<LU•W^Ngޯi."QUÉLWRک}Θ!>` 4Dzr!ITib3(iڵM;jKO9Yn;c$Q__]ɨƇD9=ը3li0$uݠ6%yQ#ojsʙ'Y^ &ibM(AgR1ַzkYXXj\jsFy77%1'Z~@9=GM\D(\SJJ9a]ka7Є|~߼vRpZ *km\BP?b񳝇Nu4.L) e|SEKIOv6|X; % * [ixq g.immRXVW9SkqARdҝy66#qDwZ-z'b@?Δv̶ m+FE"pđTWW.sv;Fn5Q4pb ex c=av`[k4 s:WZ)tJIy'K8c)W.aneƍ"''KjkkY 'O gJzŔ[9vją=$so#hG.i5NXϫՏ iy֯_?lҤI .jO}`ʥ-]ah'\I)m=Gj !ːLC^75=7 ف]),h`i{ k,WnXmϙ[/99]&m|$>:~5]ʼn``KUF햦GiB"ZAqf4SOAiw܄$KZE98 ۅ5x7_|-[Jپ} ^~ewoxU\qv6';XJ;kj^ki~siQB$׎J%dDM¹b'B( E_͋/o,Dz,͛WKϺUe)=.K {!1$K+M$C@J!Q[_#8fɒ%>ȵbŊsowC__2{ω߼ '#$28[<;Jk,'&YJ.;b+V|R0f䣝D_LO}ēO\rW7 !"^2;T͟?~gp7J,c14 `[T\Pr'* C ?C 3GfBm-?!w7ښgQ믿uه,_a@ Pꫯk޽{#G /*!##aHՁRQ" O?hp@ H)+jkk,'7##㥬,Lr#FX|ĺXxOIENDB`iptux-0.7.4/desktop/hicolor/64x64/apps/iptux.png000066400000000000000000000216661323207530100214270ustar00rootroot00000000000000PNG  IHDRF;ƒ CiCCPICC profilexڝSwX>eVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/9%bKGD pHYs.#.#x?vtIME)IDATx՛y|TUǿZ!@êHM@iqpoZG[[{GQ[Gn7VpkYDh($$’JBRۻwx^K KSzursZk^թ֭[e ןm۶@ ) 5 @a geeuY;  J$0[.w۷oRy=oՇ>}(,'c6sn448њj)_b_鱃U-gt˭=zΉ'^xLYY_f՗~sgN=iM7drIzECD)jl~6f;om/2y]w]ӧRF)ŪUz>bæR{?]ccDzV\2kpԤ%j"@p4T?^CYb(ع˗sp뭷2w\ Lss3K.w=t_Ϟ~e}&hGrhUuTXS 'D&hp(֚4t/ݲЭ3C{#; C0 Zs%ĺ5kx9d.\ΫobA 0i/fϟ?I-/9{΍.axP&-(NP]w'ii RJŮ?;A`4 Df%ׯߡ0۷o7|/TV_2G?7x%x<> 4'(;x#G1MӺpAf ۦ#ks:r"x&R|h&xC+^x^{킿0`{w#- lS|i1&:Z.p&uXFl2^ukVZB.Rqp2\?ln|>ဣ5DѼrr?{~޽;ꫯUft8 !4P8) npVIzs3֣+lSj˧xmTm q}p3GFc"z>^x|c`^xzmKOc𦦃7PvFkJ-(E\%n9 fr#QS>sv8f? (۽"JrbƌK/$<wfѢE?s/~ˀg Tl7QJYBeR5Gm쯞_3>|.S]NFJ Nl/-wOfװhѢ6'4ӞTk#/yt =`TU!Hۓr>O[WM@o'G;7~FTꨩodhsL@eq(W?gЀfQQd{@,c/ѵh4|Yv`C3RJΧH-'R6\WVa=sv筭x8dlH#5t8?OUTTFq_bD}P@ _h b囀nHɰ.]`"60n SG_V!瑤y%E]A2o޼ … iɳ\Y@i<P ~K)l =@0@ vW]z'ҚG_Os$F3)IG2 ywfn޼iyϼvOЩw_Li G9e ERqYHC'kP"/nD;@ 1x%ݺ3p-Z46ֻz&Z JS[s aI-Sֵ$Z͓[vAY7wp_U[-:n[pּ]BS$ rk]u3m:O?4*E"f̘OaFKh m %mD┑(ak5o<n_OJk7>6%e59c*O QЕ:E(Š7ǧNhc~=qux3PZhqH}+Xu([/crR|L)yڑPbzJջS XV:qtvtB)By}UodC/XiUaKYh $RJK檔BJPJ$Hiłm~1 `mQHݬ`~ŋ%{xVڧEI-;bKXc3Tאt~.[l߾fuq=ŠBMAt )nteF"']I)Q@L?ChSmG8~2:3g)XH) g")8p@ixc<ȴ4rF{`3-_~?-} xT[)e! T),6tNqC׷2·&K?,e/0mwM\JKn3&($wHCJ ]̺uazOyFdp2qh,U(V @y n;GHPl ¹7N"VxW3HITWWAd#fϱfH(E| aX88Cu !?qy_u&O JkҧuC!lh^xoZp+rIZ 9!U]"[aㄬFs=&ZjPm,)%Z)+ @"Eٹ4$)>?/<|ap$ѿqs{kBmyb߮RЎ3ZBScE7+4 4B PHz+e0^g ul .$\ĝ$0A~s `;epEm8%>Xc+Y*VZwIN ۝>x^<%%%:u&p؆uÅ*P*xhVILk|v?X_Xu1~^+ i -FX(Qͱ >FH2˘yŴ}}UČA\nӟ.i/64h#`*0S|QC-1Qץ1P6Ob4ZٱcǞ̼=Zq1PLu}mQgMȉwv9sFy%jrכۉ긫zt⌬4gt\^4PywKX>*7'n_Nrbc z呞Jj˝x< _³wMWOǢX!.6A!}s']Yme?R1G5mX@LnS5]J[4 QJ3tXL  Rf; 3,s1S[N$D<vLaم"ۭxA"/eZ*pC3^W/#{w(>86òpn (`QRP,e|v PW+[l{@Z(P9ŕ'q)>S@jhfɎJ-neZbty .bD/LHdxʥ{{{K!JmUNRȎG,?']Rec1֕9 @1ɰ'EfVQ>v:gҷs[[ay{;-QdZJvh/oZ**#x\T[ε^3wM0ӦM{nޝ3Y[QZ јZc$TX] ;o(vB3hfe ;8<Δ>L*̥kcAuY'UG֚c@y|+8??m?WWkLVOAA^ݻ.‰tct!`pkZse4M8}ӸzHC<)ҬWڽd &' E[|&ٵ&bHH[Ș-V?O=.]ԹYf yiSLϺ dlכG) 8s &$K)({5Q^LDxi9bfDE` PZ`jUO2 5kVm$9s}"S.t,]IJX;T2`78e ȟx(A*yNPƕ -,U''@VG'RR(aa8E^#O~wk׮k[>C W>;U1rn|25y a4(%l*Bi[]U@oWMH.DS8ʖ'FW)ijDŽQŽ8Jٟ[hF'K6?{7,..9.Y~{AIaD`\i_JVZM\E[UcT)>Z),YZx ǥAɠ_ePVXjFMp9WpҤIvfٳqo4F(05Bb<Vkű QZXqC{$-J2k\khEGkW7^ .邅״lٲ+>zE9KG&1 DL*AX@wJ#R)FK aSni6Cp>_4].BOFǞ8TVVǚfSU&NTu eGISChaٷOnS\rJΝq)z g]pۜk6mUӘ#ZdtRumrv-(vʐv>$#6wbbӞis 𔥏rhk<El ZMxE];z޼y g855{{Z[=ˋ~ほzL9ۄޣBVT|ʱ]82]\E"B}@5z=S&_OrKpʔ)Ma|u~'LdƍO=Ttڵ܂K;9N5b$ ]LPڶ&WSi"QPܾeSt=7k֬oᆆ=zw|}o6o7~Gعs4"kYxz4Ms+&l!3"BeU rW\tE'u$d޾}=z4PRRҿp8D:(ЫW/rrr83Sx = VQޞR5IENDB`iptux-0.7.4/desktop/iptux.desktop000066400000000000000000000015361323207530100171110ustar00rootroot00000000000000[Desktop Entry] Name=iptux Name[zh_CN]=信使(iptux) Name[zh_HK]=信使(iptux) Name[zh_TW]=信使(iptux) Name[es]=iptux Comment=LAN communication software Comment[zh_CN]=局域网通讯工具 Comment[zh_HK]=LAN 通訊工具 Comment[zh_TW]=區域網路通訊工具 Comment[es]=Software de comunicación para red local Keywords=iptux Keywords[zh_CN]=chat;talk;im;message;聊天;消息;即时通讯;飞鸽传书;飛鴿傳書;ipmsg;feige; Keywords[zh_HK]=chat;talk;im;message;聊天;訊息;即時通;飛鴿傳書;飞鸽传书;ipmsg;feige; Keywords[zh_TW]=chat;talk;im;message;聊天;訊息;即時通;飛鴿傳書;飞鸽传书;ipmsg;feige; Keywords[es]=chat;hablar;im;mensajería instantánea;mensaje;talk;message;ipmsg;feige;飞鸽传书;飛鴿傳書; Exec=iptux Terminal=false Type=Application Icon=iptux StartupNotify=true Categories=GTK;Network;InstantMessaging; iptux-0.7.4/homebrew/000077500000000000000000000000001323207530100144775ustar00rootroot00000000000000iptux-0.7.4/homebrew/iptux.rb000066400000000000000000000010171323207530100161740ustar00rootroot00000000000000require 'formula' class Iptux < Formula homepage 'https://github.com/iptux-src/iptux' url 'https://github.com/iptux-src/iptux/archive/v0.7.3.tar.gz' sha256 '287584507900a901984cff415c499fc3831c4041367b8332ab824798de1f4316' depends_on :x11 depends_on 'gettext' depends_on 'gtk+' depends_on 'jsoncpp' depends_on 'gstreamer' depends_on 'pkg-config' => :build depends_on 'cmake' => :build def install system "cmake", "-DCMAKE_INSTALL_PREFIX:PATH=#{prefix}", "." system "make", "install" end end iptux-0.7.4/pixmaps/000077500000000000000000000000001323207530100143505ustar00rootroot00000000000000iptux-0.7.4/pixmaps/CMakeLists.txt000066400000000000000000000002411323207530100171050ustar00rootroot00000000000000install(DIRECTORY icon menu tip DESTINATION ${CMAKE_INSTALL_DATADIR}/${PROJECT_NAME}/pixmaps FILE_PERMISSIONS OWNER_READ OWNER_WRITE GROUP_READ WORLD_READ ) iptux-0.7.4/pixmaps/icon/000077500000000000000000000000001323207530100153005ustar00rootroot00000000000000iptux-0.7.4/pixmaps/icon/icon-blowfish.png000066400000000000000000000033751323207530100205610ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATHYl\W;wxıl'fSiЖ!}hZZHBTm QRD 7HUiB4 YK\&'ncYzx'YX/}wt~GV۩W'|۽pjorŵ\ +=f+/j뎼A_ݮ_ˏ'ڶ=DU:fWԿ`h~ry[[V ,=[_t'`zZx}vڬ_%X}]tcMnppg௨&;Uj|nuee}u ָ.=CJ Ձ ҾՈ=4 BAW]tLN{6}}%SL8ޙ6o*Uo$3A CnoNTUL~jy} ]p)y=<>}ڗ@'hgَN>=3@erH)%kRkX?mP]݌8Y Y%p{9nE2/{xvi<|M'(L_|{xb)"nL&a mx,DQuh&k%\jw$Ȧ"zڷYYQ5R|5r*oBߋ;lTŇQTMPUcآ]S込m͏xbظe $#k뛼D?~{=G`A7ǽ5\*J2c`ŏNgF:F7qo&W=B|$)`f~b ^>l¶x+gۯ.} 6rc*^[Lh|${5HV`v#*Dx=xV ŗ$6 Z=z\?z>O&K|?Ε_~rQsݒjϤ5݋zMPf;Omo'HL<8U]4ޚ7'ɺn46޼_vC?~;1zn NR_yɨie 0gr'6sgjNHqOoߠ#B2|IENDB`iptux-0.7.4/pixmaps/icon/icon-bug.png000066400000000000000000000032541323207530100175150ustar00rootroot00000000000000PNG  IHDR;0sBIT|dcIDATH]l·wgvX&v6)viCD (PH)Rߐ*OR+ԠJ !wuu\ TWYKU.=Z<^`F:`I@lorf+c͵;I&7}zolP7A["J _u&+{@+?~L->~ORDp#- B*\M]KWQ j#ttthÆ|{UńZZqDHbPD(%-)7% d0x 5 lZyl gTFFZk+x"A@ J%\/ųmRD[B]Ba^2i9p`߶?>0U&J!R y4jrwj wj 55;=MmGKHF'_Yԋg^͢@ria %.*C6 r0 < Ν]KR wb#iDcf!@)r?`WB7?ߔ|t.IeoNӠi>@)p]p]Ҧ@pJyTBy@(_ ,xc!{+k eM# @,yD(Smx>:0ά޹s;v`yY &-5֯EL5;f2 J8p'/fA&]y|ͶiR+T4كсgKe۬1`x{auǀׁz{o_%֚I`^u\ίe(HIR04`ԁV$Jgf_"reH]Ẉr!%*~Yɞ5eP,FC/ZY|9p8"uŒ.466Z'N|.H}C`0rtRg\džJzc׮榦X 7j*9IENDB`iptux-0.7.4/pixmaps/icon/icon-cow.png000066400000000000000000000044571323207530100175360ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATHmpTswf_n6,M0 DAE?,H" _Bu* L`+Ё@mHTH0Iv&fLּZ;=}ssqxy?u0?_xrʕcG֭{eᰄZ'8,*n&O>fw9Nی`lVzGӴn2 SK[*W[ yx9N=ϗ?|3p`ɉhyYي{~ĉ;%<΁1 CSY34--w?7w}w󬢢.vthW\h3GBS !+?k9co }KG(#_iyOIiezmrsz{z@ zqFpRO kX˒qw[*Dmbz}\Kfq5h4 ADiјL$)t#P;wnI$Ei8vH >E,GWW7O(݁ /Nkvqyttt```xW_V,qܮV?пdIZr쥥hmmECC8t:6b˰nh=uIBMM K/3 U{oLDQSz̾qϯȷ!246o ظq#2 , =]Mƹsa0={utt|q\$IW"Hb|3N+fIgZQ[[ ڵkA4XQB!$I8GY3-xL&S}^~>@8&̝;5556󨪪B0$IP,Yd E?l2ךfh܉+ppL9Nb1$IZsw11hv06 ,ɓдۺPPPt: e 6'z:5k8Ji^yt qyhߏݻw#!i(*.$))NNso2DQV^&RVȊY122%+PUfL$pLغS\^$ 1A@Yy9>f,`(gXVavB@Y֤*X,Ԍ`L=[?>B4ř3gxdL&H$nz=sH$0 A(`),f$I{g˗/ݖD˗/%8υ x<)QEEQK./^SXd즥UWoq4 "JO>8?3H  !8}4>#AQ`YRQ}>'7m˂~l` AeH4Og2H%`)e٬"CUU\,t3 ^x~O:kkjJUU(2LTjhIpEUEEKm6f۶mҒY$!NO{x*PдG鼦} Rj֭Ud2 a< H"nxHRH&H&HR XVl6XV\.]We@@SLWg稢(gve!A( _ ǃ vfe!("fO7oĥK,(][fe!bݾrSx: < ~ : .;--ɿk*kj0=l\BȞ.Y_}>8y3w/{W%% [!@{R#\9la"6R l[[O?qB 7%dz!zҜ3g?Wle/AO _S޺`3791i?]| L@:8{vy X: jj"F(zAYh@eu5ZD8t4 nmb?3pah$R)/ܭ F$ea bUNwtl 0<(s0kBF\2z*p54 C)u@pjk6fT_>$h]FFH[~& JKha\4هMl!v!y4!)U4 MJ4F>d2䀬 IuP'2^ KTK~HB<,xQ׮%ī :I]g\>FM9 Up8=̞FSݩ[e֭|~~<ٳxɺ5k۬ڵ 4VO/a ,Ƕ&S)fZC7s9> 74P\SCʕR+ c>OWױx%xS9bcPD-I(jl(m۶qkk --T57c&===DW'n? ~qu@p/$܌mϝ!֭[Gww7wFV@0eʕ׳o>|0őRv88g F(̊>N&-pu5mmmq4M,hmK~<]]]b1r!͇XfӀmx:]W>ip(.v/ x.]J_e% (Nt]gxxADP `<2 {Rj0ưBr[oqrv*%PSCpIp!LttCW,[9y`n󌌼hϛ M+02d}y5ǿmF_'~)ի475#\عWݭ2[Y]` F6HB<Xm-xT +WH_¸Sa+Mq#8BrJJo)vfD{;;wH4֋Fnʻ< y~ 3%׻SQ IR[غNBJ, MU'R5_^W/M<6 'F)vM,iWUQǁ5zA)7pХM h!vKjd')*Naz-68>)Wn1WxKIENDB`iptux-0.7.4/pixmaps/icon/icon-dog.png000066400000000000000000000037621323207530100175150ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATH͖Y_U?wvvR -K[ 5 HMAۃĈ1QP$ H Z d4TJSJPZgt:|EAIN䷜GMBYx~2nݣAe腸]pbϪWW$YN4s9o%;8n4;W;gʕ7d6I dLM䶈p^audn)գkyv$Gp|:T،?,hM5V6ɛU(9x +:*Gfh5Ly.!=0,X:xw$"/:QIKd1m,ϐj˖2;: EOE_*y,ggWE^ ;vO8Ճ{-x:m`u+6پ~w-niR7vš˩/YAMx]ˉU [ #<?hcYxM^sw# qtkS嫶 < \ {z3k7{ό[ڸTZL4&:jN׃[*ꜢItؑ)Ư_CVږx:kas1k$NaZi:m]Uk(TV˞%{,s|qK%x^m¤!VXӾdq #"ŎbM!h]A!¹$qaE ǥxM?XVIJ1*<[QqW[An@a_n'I;Wq >wJL:CzpP#|X u|}ZIU[Vg2cdÅUtq,~wm ?cey3rM0*EpǭT o:yPtG G4\k+1S{. 5jX&: ߨk,)A*li\!\,͞ ? XHpSر)::^Pfo";.G9m@"|YG4P@֎j!+r9%nޱKݟMlt÷ ԑt\/\Kh{)M`0Z3LjH-iK+QX+ʻy. |оx{F(>5t_t mAӨ :m7T4c eނ ]xpk).]/[sX,JNYZhS0ja-X9cCF|`ƾšY'ȢyQTU0=GT޽m'ש[tj+m"B7X)GkӠ5JX'Vؙʎ{oB}xXW qFa:IIn~qpAG`Qah^ <:wТbO/?@ X$oU˟Κ-Qaafm^9tLq-vƁ#hƼu:e߁7]<(F />w@B})CV022BV7ƙO7=-"&> jxxJ J/Gw[~E7n3gj*O}]] _.8w]2/jY;}- . L1]D{N`~][t]gh=tWQ~_?i3Ǟ1ͷR.Sol=_߱?h5R*E#U$Rho75Yy]4w7ڰm vK {06 |:>kDQIsL\Z)t]EQ+t;34wim W5GǾvʻlHg cG;?ߋeZ>LQ9QBqA ey+x= HħH }Gy5?M ,}啿ui `ZWJt@._vl)AMMG?ևei{_/[^<i } (Rb~"K,7N57Vi 1TE!fp+`Q3+*$FSDoܹvvj)QA en]LRS!5 X[_B}]Xi"(UU5 ILRdŲ&N'⍍XE95㸔J. XWP-ˤsdSSi5q^=x'! @$CS4Ϋ `\9/B,Zol08<8N9a/~J{{O8etd,tU9r;/Ϝ駩EQ\*I1|.j:&33 WUivKݲ}4gHu@HIdSKH)1|e 52KEM%9ߞ KJ٨i| R*Xz5xA9)|);Uz>Y UV:{](m(TrH| O '|e%P__˝3 ǝm;J| ElGGU$rz` ]א)L,p -󸮋 (+/:4GXtlR"tPSmWAu]m۶ApIWl'Iy<ǫ2 4MQWkrEEUTba(! Z[[̴ svy6AI|>)!-͕utG2D&tvlO&Euu RNɩG^RɥRAU%BTU011F1 wIV,scuU|.K>}.$S X rVl8 +U[,~_;t!`L*aOCCvaݫ +rz M_B&)291[ob<9vqpÆ k7o|C}6]P8{u}iAvm0M ïa0@(b`4o#GNRȋXnU***F0nD"զib{Rj6k uQU+x HK&SIJ< 4d2H$ùagJݴiSqnuuZ˲44|x<r;v<>YB`UL˃ejH!Hd2| HDB!fdqhh={l:ߠiZ0nRHӧwYf[OOOأ~ZW-)Ta5 :8UKqU/pO^tUO6>ϸjt]FMn \m *1LoōGwzqV6.dOǭwB-f|&%-LiVY4~%Nw]6Ywy5t{(L'lD1?YOZ6,9=#%$=MYUzk/[<:wC҃.ڵt^>sr="Qcu&ܼv3ěb%2&8O#qiGw7?[١2ygft%]jl#`'&gb-uw agʒ*<ّ @@'iPqHi|*,52;D>; ^j~w9ײ`jh.fT;Df&3@k 6̖sLdR Sd\&9&3>ru+d+3$)|++Rgzy! gp} $Ll(96,C;TefKj#$WR#OR3n Eّsρ 辩zpTA/= ȗ^yVP:PA4]2p95YE+ bJauI+wN|)`D8=ʾ3טimI3?^KY\U& rvysL<ס917ĩN~Ds&枓X0nIr YE(>JV|د:$,K bm0r[Se?4FwSZDl&1t7=NBTyTh@0@V:9,zVB !H뽘_WFg_v\>3rPkJTzXܳ8z4,xt𙞃W54~G{ ͦ-*_9ZZV6o7Vk.Fʃ2B y[s3?O|60J,T7-Ss xotܱIc>xBr>4~-}"/ln|ܵTԮFcG+ \Ӣ-h4rK@IENDB`iptux-0.7.4/pixmaps/icon/icon-ghost.png000066400000000000000000000033511323207530100200620ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATHmh[+9r[%;Kl9vR<0FR[] 1,1ƶ!|A k?t8f]ʆ-c϶v[[[ ?~~A0al vE{=/..<Ϗ|>B) x(kk >84ݼw?zޯ*yVPJC>ɓ/e9Ο<^zH&(5,|>ew4B^߽{7aw?o?ۻkhnn.|o p7 D"|o&0>/ qdTJ)@ m팺`JwNg%"#"aXPj"HT*!BQdEPJa B0<TXP4@4'Ns(e0::ht$ 8ˡ+K3 ==XYYÇ SSk;G}9tww!HTieY\LynZˊ"qa8{`Yg izpG˪+j*:tHQRu ua7UUH$:33fJ)!4 v,|Yd39*ILD>G*_?zRFm%I*_::vʲR3{k:2 t])C=4 ,;Ns`C,Wk0 B\a<ZL"'b 4ͣvFJMӞHk0 ArjG"AH p;`'3Mo0R X~YNmpBHk9tb0pkV3 BT1!mLӴ3 (ZPb1;!mZ˂Չ$]׵J (5X)fQ(Zh @$/ʇS~pP8wg=vzxyx\AV ^V}Xf)LR`Y(80 SiGAN(b_E1Hix]^^^J50 :d&۷o[[[~?4MCXD$!\.0 $af(6 t.,,oݺ5~ԩW'''677W2 a`~~NOO_ Bsss$ѥkӺ>g{EQ@)Z(dtݼy-..>Pׯ_o=p8)cfWWWK&lii7t?eꨮ`=xr^>=11c]=<<`75ŋbYW&''?PkX333o[[[ܾwgr Ϗ;c?#Gpn|Ó:"x\IENDB`iptux-0.7.4/pixmaps/icon/icon-konqui.png000066400000000000000000000036271323207530100202520ustar00rootroot00000000000000PNG  IHDR;0sBIT|dNIDATH{lƿ3;3^sLy@I(bIABGPC(HUe%&M NK!1`c fwӻ;;5Hs|{uF/{%#NGdGqqet5kuOOOc2:$h7/pK) &]r3ܯ>x_9آ=WUe"$c>cV\"3pSUML%\j܌%d z%S _(r2Zkp<^tNL{Q}܂u&6KޭE'Fq\R&5ռ_uO!YErqBqkWN) ) Gz V@)tv" elXr8U#CTrvT!W&TpYh4y UA1TU"6*+/XoHcVgQZ*G4OȐ oom@QPxObNGڡUeĻEP`4$rh9c1_ 2zR| 0*|"5ŪSRExW<IJxxn̟--W"buRLo0 DlIܾ3b HqISB.}l@u4otֽa+[`6ܟ9X~%\BK[o4T(1&lJZ8s{˅~Ɏ#n4}@n0o:5Ġ uDE?9 C`\߇|:q̵ХX(-vC dM'3cel&\ : )P,L*VxeYy. |FwTy!@UUUH(hz%QҰxuG6}lS֚FAwt,;' ( Οîv$b*JP0IspO@k6Xcc>4ρsȽ1rUNCAXXl \ATa(\F@J":+[GtOUڜ;iehPFt_|dh^gD0D [|d]]] 43.~iI0&"TQIENDB`iptux-0.7.4/pixmaps/icon/icon-lion.png000066400000000000000000000047711323207530100177060ustar00rootroot00000000000000PNG  IHDR;0sBIT|d IDATHypUg{{{$$  v@K@QV;u8TZtlEjqZu  =w9,:}|y΁kj}/r˪\\t-^y_.OpG_c 7!)Z}k{] 8cAkݒ25m6wN4͞],-^ WzNJ6Yxnjs,yzǢ^`Ԫ+\4ꕊ9[{Fv͎>&1XWvoNGn~ܳԉYVzpxLuÔD0oiB/6[kS]ʡ<5v 6ڰ6ݰ`* %l(6`l^k;%ljYٻҒ5/h1.&[x^CEM*t i;W̘V);"3gpZ8cERV꡼KYߍ! D#[։IHŠD6kͿo^ HWkq"oMbmg"vRV꥾"lj&#(l%ྡu̢JJY:?:]x_=lBoz/gjkud"f^C&,`%(V0Qpk:r{Y0^<8ެ_#WO*ۥ)'P|x矼fν6^{y-F4Evl3>L*wJ%♍yQ]WϪ3uɼ݂@-p.;_*m^ H \<~3e |W}P4e5A28z..`$J|yx!&b[Bmxg߰K ]vWxl3F/:A$$ pGqzYY?7^Ja T-mRWY0%pꧮm_bXֵ95D(6MK$-|1T2y)(RSDs HCSę؋,hx =zӧǒfPh Aޱ>FNd%KK(nf``hO<,˸% Qlv[YP=H|wd@dߺhh(|ɝ3n)+4T{Yqr%uMMWX B*EղLd`5 ͬ/`jE?NrcHg=SkJWh,;$,"vDqT|> .g݂̚CґDSdrȒ ]'>t$dNrCzdnk]]R;Tu]#b Ug/bTl*eƍlã[iW,jmj t|B""XVꃑLi8 ]r^}uE,Bv{ g{Fhlh$i̳ Wqu@Ѓ>>k_VTB x(~ִ6_Ö8̆7_,LG++ i!"[>ۍ]=LRtt.ٍd&;#Wy# bv (|3)6$J*YJC'p*vAJo_Ju cIhf9vt SuIo&5ٗ0}h)k[Gr*&9FНsرl6G4FUu,u k\lFEײxZ ~_W%Iԋ P61B}X^`&?ȿC=äC㌌FIg4DQİؿ=}t4l05҆IVZ{ʢ-PLZC7 DEBGݎ GsKHH@wHi9 M0e@"5ņO <|?T|dIbyD$iCM"C%^PTZ#VQ[@00 {#8{~ͮdR`RU+u,  g;$Dؽn&hl6eZ8{Z;xE;bt 1JM(DE$ID\ #J±mBR7_kMN.uO 6 IY kƯSRj?m5Onފa6e{DI4N{7uڦ zF͠.˂Jo nsxyeKu >Y*OKiՀ.S[<}m(=cn/INIENDB`iptux-0.7.4/pixmaps/icon/icon-monkey.png000066400000000000000000000037241323207530100202440ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATH͖klw^;;]?b;^&')B@i)"JZڨHP>*ԴTmJA"" *-  Q! !F?c{}y+jG:3=ށԞgݏW]kOvڀmkzamaW}7p7Qj;8T'N,߼+օ*ޣ$ _ _N1cɢ8RKc}mFk;H!,#9M{#Hko|tzƴ^Hw{\1"yg,ӡND1l;^z&>O{9䃍s r桼uK9$ y_X;ĊG@nZ^>/JWIΙ̠>c,듵g3ֵd܋o?W=k:i3V|rL33,Lz:E%+UO1#ѺDےoK1N[h}8膅ݴX2f_K)Hdk~vtz䊧.&1w)FxRu>1G ^@eVYhϱd;^!m{Yspٝ4p;# !0·[H^B팏X(>NC pH"I>'O.xii.BPE5F@0}Lİ"F[[hicrٔSۂߨ>'roܗ5:ی6TA iҜ~ [l!i/*6n VxV)cM 2'%eeF5C^R_Ǒ}ҳ"V@XY[rƪ]Ȅ[U5)%B*I-p $5ѬNӮRJ0dN*Fݿ;\|]}v)pt7g? n%v1%0?ʦ+CΘVjPc#(5҃O@3AIPE`@|6Qm0 (tG6ZmFWN V#;xHɞRv3N}Iܪ(rÀ*CדMe[WT[1މ˾ӿ LsTuBm}6VvͩF/V.gdu"9"95v9=y,vF?Nw%-S3A! p(_"BFmJdzfmNYDE*u@o 쎧)D|dl{C  3|@ @h4@tevߺe_& .vuvdp?tn %! |{GFqdgg' ׿΢ƛ%QnZ޷֌uݭ\D˲ ɾ_)m T^P9 _1{b&@1cU7yԋ߻.sz5X#vlbbo7 DHy Oysh2P"9_mk>>f;~zC/Q=1yԾOzsyL@AQ)<@Fg6Jd\D\ 5pfzcRq޷m/6MdQ`<+L >ɢ_l?ҪxKnDc Դ]tDឮ}{yrrvR='j8E9(R:} +<RIENDB`iptux-0.7.4/pixmaps/icon/icon-penguin.png000066400000000000000000000034471323207530100204110ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATHP?{''It@Pi阉!mGlδS&3Zh?NC*F3ӨLMʴSb4`(*b 98eqq~gޙ}>yaRe!pLii69٘_*U2mڴlt:żyO>\ XQׯO۳gjN緀@L*//АBr! ~k'aDQoΧ I dcǎE2i|ify"7Kn2TVVFn`x܊ I"nIM!D53\{}љjRXXȅ (++#??\hrЀa$lt:}V/vܹ5O !v\Κ5.''̙3LXNZN}ˮ]_$*O0 5P(!νuJoo9rm"R@nn.H$B,rFFU 1x}VY5M#'' Z {NBf}Oө,֭kgFj.G9q+t_" ^ oi@:ecp2'z#]%&\x# zᨒbc)} O]M8S#z+q=dz%_TҪU1U_"+ [piLdx:8Du<67ǒ5 l #:  F[7^>ŭ^o#Q}g> DV,v1dZ`'h3-t>}2g?*2;ztO'%Wgۮ~S{#SّiV}Nvh}~SX$qIENDB`iptux-0.7.4/pixmaps/icon/icon-pig.png000066400000000000000000000043641323207530100175220ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATH{?s˲.VY@FA"DB#&TE6ڴiڦ61V`RS[JAuw5;ٙ7In&ssg\ڈc/BQs?}Bf9KnhCպд( G$S; йb틎 ! %=}amX3D=ENbNBCPs@z`˩CBhm2Htz%tPd1G;Ş60`@7ZVh*]KEUXGRTm!s<^E咍 KEQ-bh)&(? ;6]efɚCyrBqS2{RM&) A DoQKq&&qrE- " C bEVgefO; ]=tP?0H 2"\BsBsj8gvڅmݿ?;w$b44 kۃP DV+h<%Y=龓PfS-J @?۶m#N.[n|>ϦMm!o؀8 B7˗Yv|3~Әy[!`.&L__eY~=6l`h?cA< vX Դb딞Guj:a(=! oA_qO碜8T9DG/`Z+y2Gilo*wRň @@SCf*e!3_# f2hh 7 %f0 Mb!. #!ׅXu5, D'~Ov]JUmL{ %Bq0Uֆ@oP7JYh;j=>ﯹ\_xdsk-2=B<(_Z3 ZPeQg0 σvB$_ヒ@2IH7B=^hP wM`4D}LEEz{A y) W'FEfE = xxٷў-.H0͜4C %jf,?O>ꘚNdپ0P]N&W\EEұv{ f^ ~N Vx(C.5k\J'SޤWxch\Qg h/%7tՅ% `:NgwJ;?toerl.lhh 5H8Mj U jUJ%(; -m ]Hs%6C?3cҍV|&(s~R$m8Z aNPTM70L֎~\ XQ Sw޳)fk}2S^moI)g%;9 @@@T: #5(I(x+ `V >C#Wק,Zn =NQ>4'OīQ4;@UBY(Yچf D-WN;sG3@Kw=syݝ)8I3a2V*&t,[΅Wo"t)|Y+|;/~'|2 s|!1#ߙƺ~ѾUO7)HXD6BMM m?oyi||g񿔸nܲMW޲+m\b: BHqTώ}_9x4/3}ιzy.ӒH4&'&'?1^?=8M %>߬z 7? ~IENDB`iptux-0.7.4/pixmaps/icon/icon-qq.png000066400000000000000000000043301323207530100173550ustar00rootroot00000000000000PNG  IHDR:sRGBbKGD pHYs  tIME )$]&XIDATHǕWKl]W]wq⤍SINC R?(  3Č!EHH !*ʈJmMƉ>ۉg|6TE-mli-%m< IVJNs&@ܵTEcہ߸[ <*\.=9Inw{Λ;o,s0r?788ё JWR(R!W,=OM3c&3[pj<2'yǪԞsH;&`$N̡T,Srn$ruvgmsG(ת}OyFFpr$Rb0paLBeXZ^BS?lnc\)5_(oƞ=PJsP Q" #Ԇj#( b!啕c'C ䷋|^ʹѨT`iy ]DCm <Ѱְb!+%C䢇Z*SJJ$}667{"g( "\ZϜzv`uuZkc!Ev*R|Eg٧KKc>O<>CSv1Z#K3|K1P xUf)`O\kcq1Wqa2HY #$sh>HOhlw9P7:+ yM<>=UZDI@QV~?M_Ϭ=/Ͽ^riH}+_] P."4PבeQlu璘;r-;֛ۗѫ+}6ڭ\_ (Lk5\qqZt|;i} *ԳˣUŒ╖b]Ðf) aAvD4KQ{ՏnsūˣSѓDt_rk3KŜ&zmxdH YA߀g Dc ,E2.,,"L.+J ?ܭ3L]p<_ [S/ &dWcnamm kk(nag6q Fu<S-y%9!İ%NXg>[ҕK&*]X8j]ٴ6ݶ;feB$C2ljgIz| xYx7sUƹN/kշk;Ng!jW FƁ`W.b) t$Vgjg8t \; v|$!XAN!I`4ٸ}1\0',n:8o{[ Ĺr %9 X Ґ28& # 333s A223GZ˴$0"%|IqZXT(KIENDB`iptux-0.7.4/pixmaps/icon/icon-rabbit.png000066400000000000000000000032571323207530100202060ustar00rootroot00000000000000PNG  IHDR;0sBIT|dfIDATH[h\}sӌ.sŶD⺖_HTA:&׭۴5$% ֘RbL[p'!$NL1 'K\;*rHYn̹݇qZ{}!X,*ko'Oyͅ_^_xvFj6-f?OOtzNS?Ɩ4\6- >{@ X,O` MB- MT 0cSm:h P QQM&H|)ΆáCCut]G)}S暟f!іNMM1;;븮 (<!xc_Q re"\9(RJ<|qrBZ%Bhhq,~L7S’e1 xT*Ʌ 9z(Ffsa`&iyr)=-9hqG8w,ҖoHL\nӧe>30(*ZwӓJ/,zV9X/u]ar]0 R1<<g[~ (ũkի#o5`LNN%1MVEz48mX_oT|u[XV"|aY֮{P}P%p^fe`JA\#TH)RB)!Jx|\M:ޡߙ|ȡS^?^3r1ab(m|OR-Qj_wM#/>}ER?۹{Ͼ<6M"+YXa݇v<[~}=)Q b{6L)CYnewKjMM55h+lAk\T99G[lB$ٺƉƒ#lXHn~ ɦ]fiF(DI}ޜu!NZg֚i]~'k& Qg%SU8vcM3ք˞ Tg=IZim¶%BR,TdpC K8 5gK;)pöPH{4sFYF&A7: A3!Lti4Ri9Dfy-a& IENDB`iptux-0.7.4/pixmaps/icon/icon-teddybear.png000066400000000000000000000050101323207530100206730ustar00rootroot00000000000000PNG  IHDR;0sBIT|d IDATHi\U-z{zYg,&,!0@(Ha!(Z*r~A-E BL&2$齧~-$=Թ|}_b^y(|cilh-‰g5>mOwFW_ٚh#GM]_!lE{`2j 3k;;\9*O-44rE<,bp>ѓK??Q.H8r,8ޡvhzX&/,E 1I0 kO|.L9c+nvXcEa6$gళp;Xp,^>?BU#mwu]ƹ"PTiM aXzp C)%X8 4J4},ݨ;"k:jjp}pxQ`جga2_5P ¤X xu۩t@h|#I]+$XoPP^?!,ٌs* 8m\لSU&ru <^ P,k #VR+6~{u8wv!Dxt{$a NB!T |0=ϥ;4r|`,FgX+cϟBYRKeM>5bUlTSQçRO~T_X.v!e*ed%eӀW!*fϢ(XѷW`ZCaSys{k/F jXT VB1{/'?˗m7dִ1=~X C;aU-èk:R 8lh49=<>%^sˠoT~Y< Ԑ/J0 R9GkakƱ qִ9ɌdE]6/G7n?&fwdU#(t^Eb,(,:kڎx#2:`$`vZn._ՏwQJGL Vy ?څIYƑ;pK,3+,<mHy?۽#tVw+/h4!{Sb r9qbxu)qGRJ CrYRΈUEI_E]UL[WY20~&-h:":X-u%]ƠRw;:dIBw(|NFJ8kF\D0K86*Z,Q`( >$6(\^Q94(C)H]6^ Yj VU^)!ȁ]`6Bn\422.QI8-4BkEӶfKf j/8ƙKPEuv84dE(k4l !0r0Z{:P$h*ewÙSďk|U kS[eMY $)5 S **2@`8VĆסяNm󹐪Meڇu*i8R"֮nA"pvD:,VDxDelߢ47myjT"׏VJ'஑marаxfFMEEQ ˱ǙhVn8|b![P7, 17~L3iU3.BohcqtF20\.pR ҹl^l Z&$C`hU sYk(5;MorpyUY3uTΩYTl6w-I7N* &㉴#h,gkour1\ú/oF.63l~-fat11J4^JhTʦ/n;!xl|sٗ{ڽvqbۊbAQT 4 yd>MŴRE?iD8Uhld=~wx8=~4ܤgL*+\:ygҵktY+sL hS :4h87s1{,8Ǔlf)Ł⢙͖eY}P6N,^vkë˪lEۜ9y*/fɲT<1Wxo%_4LXݹ07?cީ?e_Kvq_㴲g\5EMN>7޿B>EqQIENDB`iptux-0.7.4/pixmaps/icon/icon-turtle.png000066400000000000000000000034401323207530100202540ustar00rootroot00000000000000PNG  IHDR;0sBIT|dIDATH{?󸯽]Xy-/[mZ (%T,ZM۴&MkDZcZҐj4֔KP@E].w޽Νy􏻨4$;9|眙']t8;l׭`mg̖4C7̔KSb0m-;f( !k(-P:B>\ٿឥo/?NL@#PJ6h-* .E#HtJ_+-.+={osrSa[ @)= 1BQF*} G*C@$}z-C[g٭)"$!J17qACH=:j@2R?z /MK6kMч"]tSE:BUՑG) 8Hj9wx]RëOHO^x%hTJ8F*ʽ pѲPsyȲ%%~3iM!"T>BQagC=L(B 1?x/s=󓱎ER֩gqb *J|v %K壭"lY]3x6@:yF0cYeq&v= 3Q~ÌH[H9Na(^Qv~njZv۴_~螰eMqwNjxώO`Cn[ &MxGXpxDM"J5&6@sB`y DR:4k2  ISu|-1d2I[[w\>Ϝ9X|Y /2cl[^jZ`HӦ+˾BqdҚp:V3w*TpH&hٺu+&Ν`ʕLz-/Pz^OڐJ$tS2eČ~1.كuҔg3arJ-k &$Sf!fXaaH gfC9ǘѾ65qg ͒砷fjæYysB!ZXIO~V5FD!玎˹+Ws4Q}mĞȐTI 'hLwpMd;:Z+u/JfDcf%/I%,Ὁ㙷ggNJǷmzGùܟaBD܊PTLG7onJLm~tߎ$R1 $u*Alnh7xy-R,O@ u {`k?(}"JZD,K+均}(ptUKZïOiN۶:[=3G/?Y蓡(/H˗IENDB`iptux-0.7.4/pixmaps/icon/icon-tux.png000066400000000000000000000037001323207530100175540ustar00rootroot00000000000000PNG  IHDR BsRGBbKGD pHYs  tIME *uc@IDATHǭ[lg{zg׻kf8`HQ)*6-ҾTK"C_[VR~ll 72Aݾcǎ#Lϲy~*Jٰϙч lF?6 ;i @4Be6Ms "0b7n>+ʳ(pa`̌[VjA@:Ʋ,( Q0Eij@d``܏iY8N;vl6`P(MMb߾}twu+$ %P(t钘*W._ d?m> SUmvl#@ljyK5cL\s7yYΔ(?94ܙ!k,ItY]THbߗ a&1%䞆  \}l5Ԑw8ʞ\~vC_H|}i<1UHՖgJVVԉ'i uݷ?^Vk!RT*R###O (6 !OhZTjd@H)iiiСC!4-*_F^5Mۭi7zzz.t]_E) /q,VU !uyB, !WJUki,Mt`uaǹYh<u1 ˲i~KӴϵim6Mso,"ַ }ibiO l5LX"Ll߾.lMz}D"(ibair>lOdRqR= }_Dq]Y) ٬zfmo6h̀__>QQ[$d봶y>(R_-:6~EhFkΞL}w7ϫp{IbǛ}&v>J7pk qGyxG ~|DSn޼IsS_Iܵ5 |yKLvׯ;w1:&=[\B)kXrYz6ѽ ߃VW*/N-?yR7il:MD""o\c$ルJ2F xt*##XzpԈzjw9]0Ƃf,VPAeVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/9%bKGD pHYs.#.#x?vtIME 8+mdIDAT8u]lUi~[veacl1@6,]4r#$HĀ^wBMDĘA0D&q6f +t]ۭ_=Iw'9<995F׉ lkފD؛q379J`k]2w;pٵ{)r7FؑS#tD&b-\j]D0YTW>[ 3UoNQ=fZRiS n} _@Pȁ[khhbB-bK@_+ 'M]'{{{_+|}{\-T"Qv26o:Y__o/|jq⯠@@_(aO\ɬϟWJboIye|.V]'Y a{i cŞ5X8xT7pmn*]HMUJ" IK[k0I光w٭ m`'@ Ժ8p]X(]EVCͭrx{[ M '87R;{RfR0 gEY|4Q(̕=}<|Ƒ3R9{-z}ۓ'oy.B ep_ @Wt6*<ɝ,MɏnӇ|?qqİke~M1)`T1s'΋3աo~S|)I/ߍaq# iBZ=J 7<{R~Bd.@ƽENVy1l Ł0+^ ̊f-Ϸ+;j=,ĆT/Xưr)S0dN%ST^#W-hⓊ dbIENDB`iptux-0.7.4/pixmaps/menu/menu-detect.png000066400000000000000000000066671323207530100202530ustar00rootroot00000000000000PNG  IHDR/\ CiCCPICC profilexڝSwX>eVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/9%bKGD pHYs.#.#x?vtIME5JIDAT8}Mhg3]'djjpFGkAJB/ -="<)ɄRDhi!"%4TBI4lٙyz$&x=CXvdnu瞣&sc[ I0':z&ؐ#Lu=pe3H&t>~ܖt`C'*:;4+?<<- TcZC @  vNxW=OB Gږ̵X w]BY$ zP NA1b_.ϭ2lшj_,,l)Zzdr RHmCtX]ʴvQ-C `S{ W%J[P1F0t@~yн|gD[N(D\[w[*=NW)c`D2=W?~޷)׻>Nj,75z `'}Vu7_v(}ԘKw,+loT䭊 M57n=*fF aUbfiߥ"ܭ~ygL-LʚW9 ,3 [BG~'ƞx?HeZ8Q^ƫ4<*ca1j",x2{]x7B:hٯ_=-K6 elE¶]v3 +S&MkwcV/IENDB`iptux-0.7.4/pixmaps/menu/menu-group.png000066400000000000000000000071431323207530100201250ustar00rootroot00000000000000PNG  IHDRDb CiCCPICC profilexڝSwX>eVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/9%bKGD pHYs.#.#x?vtIME)s IDAT8}[lSu?snQsC*E$$3^2%AB3L X@`1L7w]i{wOږ;:knZx>of_:&[&&y#_h绯4vľaUlG#e <L*Ӄ/v?;o]zbH)2 %e5D7$D"vXKJO.kSv'_D`ZOuo}+m9ξ;t}N'ȫp7o n r v4 .O7a===K?N,߼@nw=*8\3bß=ʅE$SPl=N]WėEl䚐-Ѳ Oc LMa:BxL[awnaeƙo8*ސ1E2DDZDKƋɼLǭJtS_v2_,cVg,Ӵ(MPB3g3V'uÏRi?N@Tga 4ʲd;<;sg,DbhXQ[(^lKas;v|%8!$t4"{g{l9y{DdOc)/OYNNK ]adC@qqJp_>FHVzPU?-WӵN?vQ#UϜZ?O;Ѭ 93i3RʧXRhHUG:BTA] ,m@߹uOp4Ľ "9UD^b8#S=ԠPTmgku|A@pswIENDB`iptux-0.7.4/pixmaps/menu/menu-share.png000066400000000000000000000070271323207530100200740ustar00rootroot00000000000000PNG  IHDR;mG MiCCPPhotoshop ICC profilexڝSwX>eVBl"#Ya@Ņ VHUĂ H(gAZU\8ܧ}zy&j9R<:OHɽH gyx~t?op.$P&W " R.TSd ly|B" I>ةآ(G$@`UR,@".Y2GvX@`B, 8C L0ҿ_pH˕͗K3w!lBa)f "#HL 8?flŢko">!N_puk[Vh]3 Z zy8@P< %b0>3o~@zq@qanvRB1n#Dž)4\,XP"MyRD!ɕ2 w ONl~Xv@~- g42y@+͗\LD*A aD@ $<B AT:18 \p` Aa!:b""aH4 Q"rBj]H#-r9\@ 2G1Qu@Ơst4]k=Kut}c1fa\E`X&cX5V5cX7va$^lGXLXC%#W 1'"O%zxb:XF&!!%^'_H$ɒN !%2I IkHH-S>iL&m O:ňL $RJ5e?2BQͩ:ZImvP/S4u%͛Cˤ-Кigih/t ݃EЗkw Hb(k{/LӗT02goUX**|:V~TUsU?y TU^V}FUP թU6RwRPQ__c FHTc!2eXBrV,kMb[Lvv/{LSCsfffqƱ9ٜJ! {--?-jf~7zھbrup@,:m:u 6Qu>cy Gm7046l18c̐ckihhI'&g5x>fob4ekVyVV׬I\,mWlPW :˶vm))Sn1 9a%m;t;|rtuvlp4éĩWggs5KvSmnz˕ҵܭm=}M.]=AXq㝧/^v^Y^O&0m[{`:>=e>>z"=#~~~;yN`k5/ >B Yroc3g,Z0&L~oL̶Gli})*2.QStqt,֬Yg񏩌;jrvgjlRlc웸xEt$ =sl3Ttcܢ˞w|/%ҟ3bKGD pHYs.#.#x?vtIME #KIDAT8ˍYlTuΝ3e,P۴Hӎu j1&!Ą\iD"&D}RQi 6,-2-tν%Η8(- zu5Gj0 u;\B]C=?mo(;uX-Mwi'ݰ9XinvliYoE~x{^ŪDt ~S}蹥ȮSO4hjw;E`e@"@xX0}dg' _3F~Y+#˔\&&4:HEoo'gJwp[WΞ?8H:QxWvtHy}=[ 8 v;26LO Jn.2; ĘFAd"{WYcqd't<2; PXYY#Xuu<~7o*%n[<} yyH@$0ɓ[:{`=@O$HdNcE"^8K*.^Tv֌0rnFQe%f &/]WW1 O{<؜Ndea:;3)ԯ"46YPL<ʪSUB!luu~?%H,Ɯ/ ~%:300T*ŷ==ʋAZR0M7ofalLd2a+o(aŲ̟ǥyy>hx@eii ]ut:a`YbD"ttNSMӊ='M0ѯ>IENDB`iptux-0.7.4/pixmaps/tip/tip-finish.png000066400000000000000000000014701323207530100177260ustar00rootroot00000000000000PNG  IHDR1_sRGBbKGD pHYs  tIME G4lIDAT8˕KSou?Csҙ.( f@B+JP*^z(CiC"2 %2Z9t]9דi9TD(!H5jl[W' IF \Pk"%8UehjS"c$EbωM sS@ a1@pه>HM).tYF!R03K\yKC-"L{>!EeV X50["}]J ɰ坹&.>,*` L#mu%Mwא/E @/B@Hz 4d-ldwR^L ȡ}DZM6S#O(2: sn;5"e!C*U"$qU=Ȍ*ĩzzOAp>1a>3D8C^BK~!igҼt{# ]NsaV]7ZDz\zlg D$C'@N,ǡJ153izwkzxp_'kEݳ'\N7ıD,Fst̹mO]]j|Ǹ!.,hSȗ,|nM~5`sРU暮͐ a3q}Oˁh+ |}IENDB`iptux-0.7.4/pixmaps/tip/tip-hide.png000066400000000000000000000015151323207530100173570ustar00rootroot00000000000000PNG  IHDR;֕JsRGBbKGD pHYs  tIME &XߴIDAT(mkfɲ,ųd;& Bֱ(tGAo#XvrtV:XZYɒ%nڲCeGg;n=} y\Jؔˆhʺ{"{fW7eg!bw( әU̗k)5]~-wecNwwIXq\ eRRJruS7ǍSe hPYUpj'E}II0hrB\$L6G,*_*> k[>g1xRy|*Cĕ_Kw9j<'PBA䅼,?NFO3t[cL'Ni>U0K6!m"ٴ` )X^CX'cDtIUQá@4WJ qILLRXXXVI2B"DVHH)QFF =? D2Bu9 i1D6Us}hI =ѣK$"^#!9!a`V$ע^R 5(lZ@1"LHKm[9T:kLǢ ۬ hU $ GX>d gy)|_,\@V{//K ǫxCuZRRy C @rfwZ. 0dPk ,]t18y(QˡKAȤxL 'ʵ ;Z48E(+a]aЎEݛ_FյEI;E[Hޮ9U(ԑ'㷯ͧcue ({p>mY;lnISIENDB`iptux-0.7.4/pixmaps/tip/tip-send.png000066400000000000000000000012601323207530100173740ustar00rootroot00000000000000PNG  IHDR/\sBIT|dgIDAT8=LSQ}}-մAbTRMdЄAb4 2%Hh$AL@E!|/|{ǡ5KιGQ\o;YiR;TĽr7:P:QZREhʞO4w_m bu)};\TT x⋙٦G=VL' ((ڰ}Û؋On BmFLz8Z0 Q8 ױjESk_BC/``;өa,' " !?Z_}{_?v7&}Kd%IqTNdoۑ8yMt$ٛz x% R saHKz*6x75bYd^NN.CX|Z8hΛ |TJnHP<9{5<(.CӎD@rV5X"H!@7u5kN:ZkR|k[rbEXjP&σAk )r(2:+hxL/`Ǯse(@)PP]"jvvW-4 /iFIENDB`iptux-0.7.4/pixmaps/tip/tip-show.png000066400000000000000000000015231323207530100174250ustar00rootroot00000000000000PNG  IHDR;֕JsRGBbKGD pHYs  tIME ?ZIDAT(]ouܯN;[vڂF k4OX^OГzZL\IHhL<i$A,qQi aYݙ '=KZLXS!1ҞTPUV8iwCՍ[?w/0@QTJutjʭ}IK{ܿzo*6")L$8XE{ gsђ|_*ܡ=B3d'LYE#%܀!6.VQ@gkMFگW.0H P *zFu{;U/ث۽KAE}잁2~(! $Te$|2wv %YU_=4yέc9L y, 2010. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: FULL NAME \n" "POT-Creation-Date: 2015-10-09 05:32+0800\n" "PO-Revision-Date: 2013-04-15 18:07+0000\n" "Last-Translator: Jakub Jezbera \n" "Language-Team: Czech \n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/AnalogFS.cpp:84 src/AnalogFS.cpp:89 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "" #: src/AnalogFS.cpp:109 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/AnalogFS.cpp:130 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "" #. Fail to determine file type, return 0 (判断文件类型失败,直接返回 0) #: src/AnalogFS.cpp:149 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/AnalogFS.cpp:161 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/AnalogFS.cpp:207 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "" #: src/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "Váš partner nepřijímá pakety. On nebo ona je možná odpojen(a)." #: src/CoreThread.cpp:231 src/DialogPeer.cpp:762 src/RecvFileData.cpp:152 #: src/RecvFileData.cpp:212 src/support.cpp:166 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Fatální chyba!!\n" "Selhání při vytváření nového socketu!\n" "%s" #: src/CoreThread.cpp:556 src/CoreThread.cpp:581 src/CoreThread.cpp:1121 #: src/CoreThread.cpp:1147 msgid "Others" msgstr "Ostatní" #: src/CoreThread.cpp:980 src/RecvFileData.cpp:133 src/RecvFileData.cpp:265 #: src/SendFileData.cpp:134 src/SendFileData.cpp:221 src/ShareFile.cpp:228 #: src/ShareFile.cpp:386 msgid "unknown" msgstr "neznámé" #: src/CoreThread.cpp:994 msgid "" msgstr "" #: src/CoreThread.cpp:1171 msgid "Broadcast" msgstr "Vysílání" #: src/DataSettings.cpp:56 msgid "Personal" msgstr "Osobní" #: src/DataSettings.cpp:58 msgid "System" msgstr "Systém" #: src/DataSettings.cpp:61 msgid "Sound" msgstr "Zvuk" #: src/DataSettings.cpp:64 msgid "Network" msgstr "Síť" #: src/DataSettings.cpp:148 msgid "Preferences" msgstr "Předvolby" #: src/DataSettings.cpp:178 msgid "Your nickname:" msgstr "Vaše přezdívka:" #: src/DataSettings.cpp:184 msgid "Please input your nickname!" msgstr "Prosím zadejte vaši přezdívku!" #: src/DataSettings.cpp:189 msgid "Your group name:" msgstr "Název vaší skupiny:" #: src/DataSettings.cpp:195 msgid "Please input your group name!" msgstr "Prosím zadejte název vaší skupiny!" #: src/DataSettings.cpp:200 msgid "Your face picture:" msgstr "Váš profilový obrázek:" #: src/DataSettings.cpp:213 msgid "Save files to: " msgstr "Uložit soubory do: " #: src/DataSettings.cpp:223 msgid "Photo" msgstr "Fotografie" #: src/DataSettings.cpp:235 msgid "Signature" msgstr "Podpis" #: src/DataSettings.cpp:266 msgid "Candidate network coding:" msgstr "" #: src/DataSettings.cpp:272 msgid "Candidate network coding" msgstr "" #: src/DataSettings.cpp:277 msgid "Preference network coding:" msgstr "Předvolby síťového kódování:" #: src/DataSettings.cpp:283 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" #: src/DataSettings.cpp:289 msgid "Pal's default face picture:" msgstr "Partnerův základní avatar:" #: src/DataSettings.cpp:302 msgid "Panel font:" msgstr "Font panelu:" #: src/DataSettings.cpp:310 msgid "Automatically open the chat dialog" msgstr "" #: src/DataSettings.cpp:315 msgid "Automatically hide the panel after login" msgstr "Automaticky skrýt panel po přihlášení" #: src/DataSettings.cpp:320 msgid "Automatically open the File Transmission Management" msgstr "Automaticky otevřít Správce přenosu souborů" #: src/DataSettings.cpp:325 msgid "Use the 'Enter' key to send message" msgstr "Používat klávesu 'Enter' k odeslání zprávy" #: src/DataSettings.cpp:330 msgid "Automatically clean up the chat history" msgstr "Automaticky smazat historii diskuze" #: src/DataSettings.cpp:335 msgid "Save the chat history" msgstr "Uložit historii diskuze" #: src/DataSettings.cpp:340 msgid "Use the Blacklist (NOT recommended)" msgstr "Použít Černou listinu (Nedoporučeno!)" #: src/DataSettings.cpp:345 msgid "Filter the request of sharing files" msgstr "Filtrovat žádosti o sdílení souborů" #: src/DataSettings.cpp:367 msgid "Activate the sound support" msgstr "Aktivovat podporu zvuku" #: src/DataSettings.cpp:374 msgid "Volume Control: " msgstr "Ovládání hlasitosi: " #: src/DataSettings.cpp:383 msgid "Sound Event" msgstr "Zvuková událost" #: src/DataSettings.cpp:411 msgid "Test" msgstr "Test" #: src/DataSettings.cpp:414 msgid "Stop" msgstr "Zastavit" #: src/DataSettings.cpp:437 msgid "From:" msgstr "Od:" #: src/DataSettings.cpp:443 msgid "Beginning of the IP(v4) section" msgstr "Začátek sekce IP(v4)" #: src/DataSettings.cpp:446 msgid "To:" msgstr "Pro:" #: src/DataSettings.cpp:452 msgid "End of the IP(v4) section" msgstr "Konec sekce IP(v4)" #: src/DataSettings.cpp:459 msgid "Add" msgstr "Přidat" #: src/DataSettings.cpp:463 msgid "Delete" msgstr "Smazat" #: src/DataSettings.cpp:469 msgid "Added IP(v4) Section:" msgstr "" #: src/DataSettings.cpp:488 msgid "Import" msgstr "Importovat" #: src/DataSettings.cpp:491 msgid "Export" msgstr "Exportovat" #: src/DataSettings.cpp:494 msgid "Clear" msgstr "Vyčistit" #: src/DataSettings.cpp:709 msgid "Transfer finished" msgstr "Přenos dokončen" #: src/DataSettings.cpp:714 msgid "Message received" msgstr "Obdržená zpráva" #: src/DataSettings.cpp:775 msgid "Play" msgstr "Přehrát" #: src/DataSettings.cpp:782 msgid "Event" msgstr "Událost" #: src/DataSettings.cpp:816 msgid "From" msgstr "Od" #: src/DataSettings.cpp:822 msgid "To" msgstr "Pro" #: src/DataSettings.cpp:830 msgid "Description" msgstr "Popis" #: src/DataSettings.cpp:847 msgid "Please select download folder" msgstr "Prosím zvolte složku pro stahování" #: src/DataSettings.cpp:869 msgid "Select Font" msgstr "Vybrat font" #: src/DataSettings.cpp:882 msgid "Please select a sound file" msgstr "Prosím vyberte zvukový soubor" #: src/DataSettings.cpp:1157 src/DataSettings.cpp:1189 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/DataSettings.cpp:1238 src/DialogGroup.cpp:647 msgid "Select All" msgstr "Vybrat vše" #: src/DataSettings.cpp:1243 src/DialogGroup.cpp:652 msgid "Reverse Select" msgstr "Obrátit výběr" #: src/DataSettings.cpp:1248 src/DialogGroup.cpp:657 msgid "Clear Up" msgstr "Vyčistit" #: src/DataSettings.cpp:1342 src/RevisePal.cpp:426 msgid "Please select a face picture" msgstr "Prosím vyberte profilový obrázek" #: src/DataSettings.cpp:1365 msgid "Please select a personal photo" msgstr "Prosím vyberte osobní fotografii" #: src/DataSettings.cpp:1509 src/DataSettings.cpp:1516 src/DetectPal.cpp:122 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Neplatná IP(v4) adresa: %s!" #: src/DataSettings.cpp:1614 msgid "Please select a file to import data" msgstr "Prosím vyberte soubor pro import dat" #: src/DataSettings.cpp:1662 msgid "Save data to file" msgstr "Uložit data do souboru" #: src/DetectPal.cpp:70 msgid "Detect pals" msgstr "Detekovat partnery" #: src/DetectPal.cpp:72 msgid "Detect" msgstr "Rozpoznat" #: src/DetectPal.cpp:73 src/ShareFile.cpp:107 msgid "Cancel" msgstr "Zrušit" #: src/DetectPal.cpp:91 msgid "Please input an IP address (IPv4 only):" msgstr "Prosím zadejte IP adresu (pouze IPv4):" #: src/DetectPal.cpp:99 msgid "Please input an IP address (IPv4 only)!" msgstr "Prosím zadejte IP adresu (pouze IPv4)!" #: src/DetectPal.cpp:127 #, c-format msgid "The notification has been sent to %s." msgstr "Bylo zasláno upozornění pro %s." #: src/dialog.cpp:34 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "Přenos souboru nebyl dokončen.\n" "Opravdu chcete odejít?" #: src/dialog.cpp:37 msgid "Confirm Exit" msgstr "Potvrďte ukončení" #: src/dialog.cpp:57 src/DialogPeer.cpp:379 src/MainWindow.cpp:1597 msgid "Request Shared Resources" msgstr "Zažádat sdílení zdrojů" #: src/dialog.cpp:60 msgid "Agree" msgstr "Souhlasím" #: src/dialog.cpp:61 src/DialogPeer.cpp:848 msgid "Refuse" msgstr "Odmítnout" #: src/dialog.cpp:74 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/dialog.cpp:103 msgid "Access Password" msgstr "Přístupové heslo" #: src/dialog.cpp:110 msgid "Please input the password for the shared files behind" msgstr "Prosím zadejte heslo pro sdílené soubory" #: src/dialog.cpp:123 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Heslo:" #: src/dialog.cpp:140 src/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Prázdné heslo!" #: src/dialog.cpp:163 msgid "Enter a New Password" msgstr "Zadat nové heslo" #: src/dialog.cpp:173 msgid "Password: " msgstr "Heslo: " #: src/dialog.cpp:181 msgid "Repeat: " msgstr "Zopakovat: " #: src/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Neshoda hesel!" #: src/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "Vyberte prosím složku do které chcete uložit soubory." #: src/DialogGroup.cpp:277 #, c-format msgid "Talk with the group %s" msgstr "Hovořit se skupinou %s" #: src/DialogGroup.cpp:371 msgid "Member" msgstr "Člen" #: src/DialogGroup.cpp:465 msgid "Send" msgstr "Odeslat" #: src/DialogGroup.cpp:472 msgid "Pals" msgstr "Partneři" #: src/DialogGroup.cpp:495 src/DialogPeer.cpp:409 src/MainWindow.cpp:865 msgid "_Tools" msgstr "_Nástroje" #: src/DialogGroup.cpp:501 src/DialogPeer.cpp:417 msgid "Clear Buffer" msgstr "" #: src/DialogGroup.cpp:508 msgid "Sort" msgstr "Třídit" #: src/DialogGroup.cpp:514 src/MainWindow.cpp:904 msgid "By Nickname" msgstr "Podle přezdívky" #: src/DialogGroup.cpp:521 src/MainWindow.cpp:911 msgid "By IP" msgstr "Podle IP" #: src/DialogGroup.cpp:531 src/MainWindow.cpp:921 msgid "Ascending" msgstr "Vzestupně" #: src/DialogGroup.cpp:538 src/MainWindow.cpp:928 msgid "Descending" msgstr "Sestupně" #: src/DialogPeer.cpp:231 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Komunikace s %s(%s) IP:%s" #: src/DialogPeer.cpp:329 msgid "Info." msgstr "Informace." #: src/DialogPeer.cpp:363 src/MainWindow.cpp:819 msgid "_File" msgstr "_Soubor" #: src/DialogPeer.cpp:367 msgid "Attach File" msgstr "Přiložit soubor" #: src/DialogPeer.cpp:373 msgid "Attach Folder" msgstr "Přiložit složku" #: src/DialogPeer.cpp:389 msgid "Close" msgstr "Zavřít" #: src/DialogPeer.cpp:413 msgid "Insert Picture" msgstr "Vložit obrázek" #: src/DialogPeer.cpp:438 src/MainWindow.cpp:1653 #, c-format msgid "Version: %s\n" msgstr "Verze: %s\n" #: src/DialogPeer.cpp:442 src/MainWindow.cpp:1657 #, c-format msgid "Nickname: %s@%s\n" msgstr "Přezdívka: %s@%s\n" #: src/DialogPeer.cpp:444 src/MainWindow.cpp:1659 #, c-format msgid "Nickname: %s\n" msgstr "Přezdívka: %s\n" #: src/DialogPeer.cpp:447 src/MainWindow.cpp:1662 #, c-format msgid "User: %s\n" msgstr "Uživatel: %s\n" #: src/DialogPeer.cpp:450 src/MainWindow.cpp:1665 #, c-format msgid "Host: %s\n" msgstr "" #: src/DialogPeer.cpp:455 src/MainWindow.cpp:1670 #, c-format msgid "Address: %s(%s)\n" msgstr "Adresa: %s(%s)\n" #: src/DialogPeer.cpp:457 src/MainWindow.cpp:1672 #, c-format msgid "Address: %s\n" msgstr "Adresa: %s\n" #: src/DialogPeer.cpp:461 src/MainWindow.cpp:1676 #, c-format msgid "Compatibility: Microsoft\n" msgstr "Kompatibilita: Microsoft\n" #: src/DialogPeer.cpp:463 src/MainWindow.cpp:1678 #, c-format msgid "Compatibility: GNU/Linux\n" msgstr "Kompatibilita: GNU/Linux\n" #: src/DialogPeer.cpp:466 src/MainWindow.cpp:1681 #, c-format msgid "System coding: %s\n" msgstr "Systémové kódování: %s\n" #: src/DialogPeer.cpp:470 src/MainWindow.cpp:1685 msgid "Signature:\n" msgstr "Podpis:\n" #: src/DialogPeer.cpp:477 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Fotografie:\n" #: src/DialogPeer.cpp:722 msgid "Please select a picture to insert the buffer" msgstr "" #: src/DialogPeer.cpp:789 msgid "Enclosure." msgstr "" #: src/DialogPeer.cpp:836 msgid "File to be receive." msgstr "" #: src/DialogPeer.cpp:840 msgid "Receiving progress." msgstr "Stav přenosu." #: src/DialogPeer.cpp:843 msgid "Accept" msgstr "Přijmout" #: src/DialogPeer.cpp:853 msgid "Detail" msgstr "" #: src/DialogPeer.cpp:884 msgid "File received." msgstr "Soubor přenesen." #: src/DialogPeer.cpp:926 src/DialogPeer.cpp:990 msgid "Source" msgstr "Zdroj" #: src/DialogPeer.cpp:932 msgid "SaveAs" msgstr "Uložit jako" #: src/DialogPeer.cpp:937 src/DialogPeer.cpp:1000 src/MainWindow.cpp:1213 #: src/ShareFile.cpp:280 msgid "Size" msgstr "Velikost" #: src/DialogPeer.cpp:995 msgid "Name" msgstr "Název" #: src/DialogPeer.cpp:1096 src/DialogPeer.cpp:1169 #, c-format msgid "Receiving Progress." msgstr "Stav přenosu." #: src/DialogPeer.cpp:1099 src/DialogPeer.cpp:1172 #, c-format msgid "%s to Receive." msgstr "" #: src/DialogPeer.cpp:1103 src/DialogPeer.cpp:1176 #, c-format msgid "%s Of %s Received." msgstr "" #: src/DialogPeer.cpp:1109 #, c-format msgid "Mission Completed!" msgstr "" #: src/DialogPeer.cpp:1321 msgid "Remove Selected" msgstr "Smazat vybrané" #: src/HelpDialog.cpp:61 src/HelpDialog.cpp:66 msgid "Jally " msgstr "Jally " #: src/HelpDialog.cpp:62 src/HelpDialog.cpp:68 msgid "ManPT " msgstr "ManPT " #: src/HelpDialog.cpp:67 msgid "LiWeijian " msgstr "LiWeijian " #: src/HelpDialog.cpp:71 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT " #: src/HelpDialog.cpp:80 src/MainWindow.cpp:576 src/StatusIcon.cpp:106 #: src/StatusIcon.cpp:277 msgid "iptux" msgstr "iptux" #: src/HelpDialog.cpp:85 msgid "A GTK+ based LAN Messenger." msgstr "LAN komunikátor založený na GTK+" #: src/HelpDialog.cpp:102 msgid "Help" msgstr "Pomoc" #: src/HelpDialog.cpp:102 msgid "Contributers" msgstr "Přispěvatelé" #: src/HelpDialog.cpp:102 src/HelpDialog.cpp:120 msgid "..." msgstr "..." #: src/HelpDialog.cpp:104 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/HelpDialog.cpp:110 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/HelpDialog.cpp:128 msgid "More About Iptux" msgstr "Více o Iptux" #: src/LogSystem.cpp:53 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Obdrženo od: Přezdívka:%s Uživatel:%s Počítač:%s" #: src/LogSystem.cpp:57 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/LogSystem.cpp:60 msgid "Send-Broadcast" msgstr "" #: src/LogSystem.cpp:83 #, c-format msgid "User:%s Host:%s" msgstr "Uživatel:%s Počítač:%s" #: src/MainWindow.cpp:603 msgid "Files Transmission Management" msgstr "Manažer přenosu souborů" #: src/MainWindow.cpp:718 msgid "Pals Online: 0" msgstr "Partnerů online: 0" #: src/MainWindow.cpp:801 msgid "Search Pals" msgstr "Vyhledat partnery" #: src/MainWindow.cpp:824 src/StatusIcon.cpp:185 msgid "_Detect" msgstr "_Zjistit" #: src/MainWindow.cpp:833 msgid "_Find" msgstr "_Najít" #: src/MainWindow.cpp:845 src/StatusIcon.cpp:194 msgid "_Quit" msgstr "_Odejít" #: src/MainWindow.cpp:871 src/StatusIcon.cpp:164 msgid "_Preferences" msgstr "_Předvolby" #: src/MainWindow.cpp:880 src/StatusIcon.cpp:156 msgid "_Transmission" msgstr "_Přenosy" #: src/MainWindow.cpp:889 src/StatusIcon.cpp:173 msgid "_Shared Management" msgstr "Správa _sdílení" #: src/MainWindow.cpp:898 msgid "_Sort" msgstr "_Třídit" #: src/MainWindow.cpp:936 msgid "_Update" msgstr "_Aktualizovat" #: src/MainWindow.cpp:953 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/MainWindow.cpp:957 msgid "_Help" msgstr "_Pomoc" #: src/MainWindow.cpp:965 msgid "_More" msgstr "_Více" #: src/MainWindow.cpp:969 msgid "_FAQ" msgstr "_FAQ" #: src/MainWindow.cpp:1121 msgid "Nickname" msgstr "Ptřezdívka" #: src/MainWindow.cpp:1132 msgid "Group" msgstr "Skupina" #: src/MainWindow.cpp:1138 src/MainWindow.cpp:1201 msgid "IPv4" msgstr "IPv4" #: src/MainWindow.cpp:1144 msgid "User" msgstr "Uživatel" #: src/MainWindow.cpp:1150 msgid "Host" msgstr "Počítač" #: src/MainWindow.cpp:1183 msgid "State" msgstr "Status" #: src/MainWindow.cpp:1189 msgid "Task" msgstr "Úkol" #: src/MainWindow.cpp:1195 msgid "Peer" msgstr "" #: src/MainWindow.cpp:1207 msgid "Filename" msgstr "Název souboru" #: src/MainWindow.cpp:1219 msgid "Completed" msgstr "Dokončeno" #: src/MainWindow.cpp:1225 msgid "Progress" msgstr "Postup" #: src/MainWindow.cpp:1231 msgid "Cost" msgstr "Náklady" #: src/MainWindow.cpp:1237 msgid "Remaining" msgstr "Zbývá" #: src/MainWindow.cpp:1243 msgid "Rate" msgstr "Rychlost" #: src/MainWindow.cpp:1534 msgid "Open This File" msgstr "Otevřít tento soubor" #: src/MainWindow.cpp:1540 msgid "Open Containing Folder" msgstr "Otevřít složku" #: src/MainWindow.cpp:1546 msgid "Terminate Task" msgstr "Ukončit úkol" #: src/MainWindow.cpp:1551 msgid "Terminate All" msgstr "Ukončit vše" #: src/MainWindow.cpp:1556 msgid "Clear Tasklist" msgstr "Vyčistit seznam úkolů" #: src/MainWindow.cpp:1577 msgid "Send Message" msgstr "Odeslat zprávu" #: src/MainWindow.cpp:1611 msgid "Change Info." msgstr "Změnit informace" #: src/MainWindow.cpp:1626 msgid "Delete Pal" msgstr "Smazat partnera" #: src/MainWindow.cpp:1715 #, c-format msgid "Pals Online: %" msgstr "" #: src/MainWindow.cpp:1946 msgid "The file you want to open not exist!" msgstr "Soubor, který chcete otevřít neexistuje!" #: src/MainWindow.cpp:1975 msgid "The path you want to open not exist!" msgstr "Složka, kterou chcete otevřít neexistuje!" #: src/output.cpp:35 msgid "Infomation" msgstr "Informace" #: src/output.cpp:60 msgid "Warning" msgstr "Varování" #: src/output.cpp:83 msgid "Error" msgstr "Chyba" #: src/ProgramData.cpp:216 msgid "utf-16" msgstr "utf-16" #: src/ProgramData.cpp:219 msgid "utf-8" msgstr "utf-8" #: src/RecvFileData.cpp:117 msgid "receive" msgstr "" #: src/RecvFileData.cpp:184 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Selhání při získávání souboru \"%s\" od %s!" #: src/RecvFileData.cpp:187 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Soubor \"%s\" od %s přenesen úspěšně!" #: src/RecvFileData.cpp:332 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/RecvFileData.cpp:335 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Změnit informace o partnerovi" #: src/RevisePal.cpp:125 msgid "Pal's nickname:" msgstr "Partnerova přezdívka:" #: src/RevisePal.cpp:131 msgid "Please input pal's new nickname!" msgstr "Prosím zadejte novou partnerovu přezdívku!" #: src/RevisePal.cpp:137 msgid "Pal's group name:" msgstr "Název partnerovy skupiny:" #: src/RevisePal.cpp:143 msgid "Please input pal's new group name!" msgstr "" #: src/RevisePal.cpp:149 msgid "System coding:" msgstr "Systémové kódování:" #: src/RevisePal.cpp:155 msgid "Be SURE to know what you are doing!" msgstr "Ujistěte se, že víte co děláte!" #: src/RevisePal.cpp:161 msgid "Pal's face picture:" msgstr "" #: src/RevisePal.cpp:175 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/SendFileData.cpp:117 msgid "send" msgstr "odesláno" #: src/SendFileData.cpp:162 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/SendFileData.cpp:165 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Odeslání souboru \"%s\" pro %s bylo úspěšné!" #: src/SendFileData.cpp:290 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/SendFileData.cpp:293 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/ShareFile.cpp:102 msgid "Shared Files Management" msgstr "" #: src/ShareFile.cpp:105 msgid "OK" msgstr "OK" #: src/ShareFile.cpp:106 msgid "Apply" msgstr "Použít" #: src/ShareFile.cpp:150 msgid "Add Files" msgstr "Přidat soubory" #: src/ShareFile.cpp:153 msgid "Add Folders" msgstr "Přidat složky" #: src/ShareFile.cpp:156 msgid "Delete Resources" msgstr "Smazat zdroje" #: src/ShareFile.cpp:159 msgid "Clear Password" msgstr "Smazat heslo" #: src/ShareFile.cpp:162 msgid "Set Password" msgstr "Nastavit heslo" #: src/ShareFile.cpp:220 src/ShareFile.cpp:378 msgid "regular" msgstr "" #: src/ShareFile.cpp:224 src/ShareFile.cpp:382 msgid "directory" msgstr "složka" #: src/ShareFile.cpp:270 msgid "File" msgstr "Soubor" #: src/ShareFile.cpp:286 msgid "Type" msgstr "Druh" #: src/ShareFile.cpp:422 msgid "Choose the files to share" msgstr "Vyberte soubory ke sdílení" #: src/ShareFile.cpp:425 msgid "Choose the folders to share" msgstr "Vybrat složky ke sdílení" #: src/SoundSystem.cpp:153 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/StatusIcon.cpp:102 src/StatusIcon.cpp:274 #, c-format msgid "To be read: %u messages" msgstr "" #: src/StatusIcon.cpp:143 msgid "_Hide" msgstr "_Skrýt" #: src/StatusIcon.cpp:145 msgid "_Show" msgstr "_Zobrazit" #: src/support.cpp:44 msgid "Loading the process successfully!" msgstr "" #: src/support.cpp:63 msgid "The process is about to quit!" msgstr "" #: src/support.cpp:102 #, c-format msgid "iptux: A software for sharing in LAN\n" msgstr "iptux: Software pro sdílení v síti LAN\n" #: src/support.cpp:103 #, c-format msgid "" "\t-h --help\n" "\t\tdisplay this help and exit\n" msgstr "" #: src/support.cpp:104 #, c-format msgid "" "\t-v --version\n" "\t\toutput version information and exit\n" msgstr "" #: src/support.cpp:120 #, c-format msgid "What do you want to do?\n" msgstr "Co chcete dělat?\n" #: src/support.cpp:149 msgid "Can't find any available web browser!\n" msgstr "" #: src/support.cpp:179 #, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(2425)!\n" "%s" msgstr "" #: src/UdpData.cpp:133 src/UdpData.cpp:134 src/UdpData.cpp:569 #: src/UdpData.cpp:606 msgid "mysterious" msgstr "záhadný" #: src/uninstall/utils.cpp:23 msgid "The user is not privileged!\n" msgstr "Uživatel nemá oprávnění!\n" #: src/uninstall/utils.cpp:34 #, c-format msgid "Opendir() directory \"%s\" failed, %s\n" msgstr "" #: src/uninstall/utils.cpp:45 #, c-format msgid "Stat() file \"%s\" failed, %s\n" msgstr "" #: src/uninstall/utils.cpp:51 src/uninstall/utils.cpp:67 #, c-format msgid "Unlink() file \"%s\" failed, %s\n" msgstr "" #: src/uninstall/utils.cpp:61 #, c-format msgid "Rmdir() directory \"%s\" failed, %s\n" msgstr "" iptux-0.7.4/po/de.po000066400000000000000000000717561323207530100142550ustar00rootroot00000000000000# German translation for iptux # Copyright (c) 2009 Rosetta Contributors and Canonical Ltd 2009 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2009. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2018-01-22 06:45+0000\n" "Last-Translator: zhangjiejing \n" "Language-Team: German \n" "Language: de\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Leeres Passwort!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Ungültige IP(v4)-Adresse: %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Passwörter stimmen nicht überein!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Foto:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "%s von %s empfangen." #: src/iptux/DialogBase.cpp:869 #, fuzzy, c-format msgid "%s Of %s Sent." msgstr "%s von %s empfangen." #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "%s zu empfangen." #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Passwort:" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "iptux: Ein Programm für den Austausch im LAN\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "…" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "Ein LAN-Sofortnachrichtenprogramm basierend auf GTK+." #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "Annehmen" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Passwort für Zugriff" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Soundunterstützung aktivieren" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Hinzufügen" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Dateien hinzufügen" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Ordner hinzufügen" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Hinzugefügter IP(v4)-Abschnitt:" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "Adresse: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Adresse: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Annehmen" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Übernehmen" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "Aufsteigend" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Datei anhängen" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Ordner anhängen" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Den Chatverlauf automatisch löschen" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Das Panel automatisch nach dem Login verstecken" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Automatisch die Dateiübertragungsverwaltung öffnen" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Chat-Dialog automatisch öffnen" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "Sie sollten WISSEN, was Sie machen!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Kompatibilität mit dem iptux-Protokoll wahren (gefährlich!)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Anfang des IP(v4)-Abschnitts" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Übertragung" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "Nach IP-Adresse" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Nach Spitznamen" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "Es kann kein verfügbarer Webbrowser gefunden werden!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Abbrechen" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "Informationen bearbeiten." #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Informationen zum Freund ändern" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Den Chatverlauf speichern" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 #, fuzzy msgid "Choose enclosure folders" msgstr "Ordner zum Freigeben wählen" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "Dateien zum Freigeben wählen" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "Ordner zum Freigeben wählen" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Leeren" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Zwischenspeicher leeren" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Passwort zurücksetzen" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Aufgabenliste leeren" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Leeren" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Schließen" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Kompatibilität: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Kompatibilität: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "Abgeschlossen" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Beenden bestätigen" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Mitwirkende" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "Kosten" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Löschen" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Freund löschen" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "Daten löschen" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Absteigend" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Beschreibung" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Finden" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Freunde finden" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Ende des IP(v4)-Abschnitts" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Neues Passwort eingeben" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Fehler" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Ereignis" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Exportieren" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "Der Anfragenton konnte nicht abgespielt werden, %s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "Empfangen des Ordners »%s« von %s gescheitert!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Empfangen der Datei »%s« von %s gescheitert!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "Senden des Ordners »%s« an %s gescheitert!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "Senden der Datei »%s« an %s gescheitert!" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Schwerer Fehler!!\n" "Verwendung des TCP/UDP-Ports 2425 fehlgeschlagen!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Schwerwiegender Fehler!!\n" "Erstellen eines neuen Sockets fehlgeschlagen!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Schwerer Fehler!!\n" "Verwendung des TCP/UDP-Ports 2425 fehlgeschlagen!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Schwerwiegender Fehler!!\n" "Erstellen eines neuen Sockets fehlgeschlagen!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "Datei" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "Datei empfangen." #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "Datei zu Empfangen" #: src/iptux/DialogBase.cpp:719 #, fuzzy msgid "File to send." msgstr "Datei zu Empfangen" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "Die Dateiübertragung ist noch nicht abgeschlossen.\n" "Sind Sie sicher, dass Sie abbrechen und beenden möchten?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "Dateiname" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "Datei" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "Dateiübertragungen-Verwaltung" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Anfrage zum Dateiaustausch filtern" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fopen() der Datei \"%s\" schlug fehl!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "Von" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "Von:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "Gruppe" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Hilfe" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "Host" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Host: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importieren" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Informationen." #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Information" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Bild einfügen" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "Es ist eine Ehre für iptux, dass es von vielen freiwilligen Helfern " "mitentwickelt wurde. Ohne ihre Hilfe wäre aus iptux nie etwas geworden.\n" "\n" "Einigen möchten wir besonders danken:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "LiWeijian " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "Laden des Prozesses erfolgreich!" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Mitglied" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Nachricht erhalten" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "Vorgang abgeschlossen!" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() des Verzeichnisses \"%s\" fehlgeschlagen, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "Mehr Informationen zu Iptux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "Name" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Netzwerk" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "Spitzname" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Spitzname: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Spitzname: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "Ok" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "Beinhaltenden Ordner öffnen" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "Diese Datei öffnen" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() der Datei \"%s\" fehlgeschlagen, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() des Verzeichnisses \"%s\" fehlgeschlagen, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Sonstiges" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Standardprofilbild für Freunde:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "Bild des Freundes" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Gruppenname des Freundes:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Nickname des Freundes" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Freunde" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "Freunde online: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "Freunde online: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Panel-Schriftart" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Passwort: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 #, fuzzy msgid "PeelName" msgstr "Name" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "Peer" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Persönliches" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Abspielen" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Bitte geben Sie eine IP-Adresse (nur IPv4) ein!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Bitte geben Sie eine IP-Adresse (nur IPv4) ein:" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Bitte geben Sie den neuen Gruppennamen des Freundes ein!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Bitte geben Sie den neuen Nicknamen des Freundes ein!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Bitte geben Sie das Passwort für die Freigabe ein" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Bitte geben Sie Ihren Gruppenname ein!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Bitte geben Sie Ihren Spitznamen ein!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Bitte wählen Sie ein Profilbild" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Bitte wählen sie die Datei, aus der importiert werden soll" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "Bitte wählen Sie einen Ordner zum Speichern von Dateien." #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Bitte wählen Sie ein persönliches Foto" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "Bitte wählen Sie ein Bild zum Einfügen aus" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Bitte wählen Sie eine Sounddatei aus" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Bitte wählen Sie den Download-Ordner" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Einstellungen" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "Fortschritt" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "Geschwindigkeit" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "Ordner »%s« erfolgreich von %s empfangen!" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Datei »%s« erfolgreich von %s empfangen!" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "Empfangfortschritt." #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "Empfangsfortschritt." #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Empfangen von: Spitzname: %s Benutzer: %s Host: %s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Ablehnen" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "Verbleibend" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "Ausgewählte entfernen" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Wiederholen: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Freigabe anfordern" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Auswahl umkehren" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Daten in Datei speichern" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Dateien speichern unter: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Den Chatverlauf speichern" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "Speichern unter" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "Freunde suchen" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Alles auswählen" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Schriftart auswählen" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Senden" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Nachricht senden" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "Ordner »%s« erfolgreich an %s gesendet!" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Datei »%s« erfolgreich an %s gesendet!" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "Broadcast senden" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "Senden zu: Spitzname: %s Benutzer: %s Host: %s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "Empfangfortschritt." #: src/iptux/DialogBase.cpp:724 #, fuzzy msgid "Sending progress." msgstr "Empfangsfortschritt." #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Passwort festlegen" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "Freigabenverwaltung" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Signatur" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "Signatur:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "Größe" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Sortieren" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Sound" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Klangereignis" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "Quelle" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() der Datei \"%s\" fehlgeschlagen, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "Status" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Stopp" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "System" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "System-Codierung:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "System-Codierung: %s\n" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Mit %s(%s) IP:%s sprechen" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Mit der Gruppe %s sprechen" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "Aufgabe" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Alle abbrechen" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "Aufgabe abbrechen" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Test" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "Die Datei, die geöffnet werden soll, existiert nicht!" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "Die Benachrichtigung wurde an %s gesendet." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "Der Pfad, der geöffnet werden soll, existiert nicht!" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "Der Prozess wird gerade beendet!" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "An" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "Ungelesen: %u Nachrichten" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "An:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Übertragung abgeschlossen" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "Typ" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Benutzen Sie die 'Enter'-Taste um die Nachricht zu senden" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Die Blacklist verwenden (NICHT empfohlen)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "Benutzer" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "Benutzer: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "Benutzer: %s Host: %s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Version: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Lautstäreregelung: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Warnung" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Ihr Profilbild:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Ihr Gruppenname:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Ihr Spitzname:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Ihr Freund (%s)[%s]\n" "möchte auf Ihre Freigabe zugreifen.\n" "Sind Sie einverstanden?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" "Ihr Freund hat das Paket nicht erhalten. Er oder sie ist vielleicht offline." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Erkennen" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "_FAQ" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_Datei" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Suchen" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "_Hilfe" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "_Verstecken" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "_Mehr" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "_Einstellungen" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Beenden" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "_Freigaben verwalten" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "_Anzeigen" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "_Sortieren" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Werkzeuge" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "Über_tragung" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "_Aktualisieren" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "Ordner" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "iptux" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "mysteriös" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "empfangen" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "regelmäßig" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "Senden" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "Unbekannt" #~ msgid "" #~ "\t-h --help\n" #~ "\t\tdisplay this help and exit\n" #~ msgstr "" #~ "\t-h --help\n" #~ "\t\tDiese Hilfe zeigen und beenden\n" #~ msgid "" #~ "\t-v --version\n" #~ "\t\toutput version information and exit\n" #~ msgstr "" #~ "\t-v --version\n" #~ "\t\tVersionsinformationen anzeigen und beenden\n" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "Opendir() Ordner \"%s\" fehlgeschlagen, %s\n" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "Rmdir() Ordner \"%s\" fehlgeschlagen, %s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "Stat() Datei \"%s\" fehlgeschlagen, %s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "Der Benutzer hat nicht die erforderliche Berechtigung!\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "Unlink() Datei \"%s\" fehlgeschlagen, %s\n" #~ msgid "What do you want to do?\n" #~ msgstr "Was möchten Sie machen?\n" #~ msgid "utf-16" #~ msgstr "UTF-16" #~ msgid "utf-8" #~ msgstr "UTF-8" iptux-0.7.4/po/en_GB.po000066400000000000000000000566011323207530100146270ustar00rootroot00000000000000# English (United Kingdom) translation for iptux # Copyright (c) 2009 Rosetta Contributors and Canonical Ltd 2009 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2009. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2018-01-22 06:45+0000\n" "Last-Translator: zhangjiejing \n" "Language-Team: English (United Kingdom) \n" "Language: en_GB\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "" #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "A GTK+ based LAN Messenger." #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Add" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Add Files" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Add Folders" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Address: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Agree" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Apply" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Broadcast" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "By IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "By Nickname" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Cancel" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Clear" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Clear Buffer" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Clear Password" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Clear Tasklist" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Clear Up" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Close" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Compatibility: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Compatibility: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Contributers" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Delete" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Delete Pal" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Detect" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Error" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Event" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Export" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "_File" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Help" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Host: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Import" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "" #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Infomation" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Insert Picture" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Nickname: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Nickname: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "OK" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Others" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Pal's group name:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Pal's nickname:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Password: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Personal" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Play" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Please input pal's new group name!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Please input pal's new nickname!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Refuse" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Repeat: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "" #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Send" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Send Message" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Set Password" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Sort" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Sound" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Sound Event" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Stop" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "System" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Terminate All" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "User: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Version: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Volume Control: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Warning" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Your group name:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Your nickname:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "Your pal didn't receive the packet. He or she is offline maybe." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Detect" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_File" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Find" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "_Help" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "_Hide" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "_More" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Quit" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "_Show" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Tools" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "_Update" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "directory" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "iptux" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "mysterious" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "receive" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "regular" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "send" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "unknown" #~ msgid "The user is not privileged!\n" #~ msgstr "The user is not privileged!\n" iptux-0.7.4/po/es.po000066400000000000000000000731521323207530100142640ustar00rootroot00000000000000# Spanish translation for iptux # Copyright (c) 2009 Rosetta Contributors and Canonical Ltd 2009 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2009. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2013-06-05 13:46-0300\n" "Last-Translator: Fernando Toledo \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" "X-Launchpad-Export-Date: 2010-04-01 12:32+0000\n" "X-Generator: Launchpad (build Unknown)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Clave vacía!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Dirección IP(v4) inválida: %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Las claves son distintas!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Foto:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Clave:" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "iptux: Un software para compartir en LAN\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "Un mensajero de red basando en GTK+." #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "Aceptar" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Clave de Acceso" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Activar soporte de sonido" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Agregar" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Añadir archivos" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Añadir directorios" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Secciones IP(v4) agregadas:" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "Dirección: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Dirección: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "De acuerdo" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Aplicar" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "Ascendente" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Adjuntar Archivo" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Adjuntar Directorio" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Limpiar automáticamente el historial" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Ocultar automáticamente el panel después de ingresar" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Abrir automáticamente el Administrador de Transferencias" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Abrir automáticamente la ventana de chat" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "Esté SEGURO de saber lo que va a hacer!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Ser compatible con el protocolo iptux's (PELIGROSO)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Comienzo de la sección IP (v4)" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Difusión" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "Por IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Por Apodo" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "No se puede encontrar ningún navegador web disponible!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Cancelar" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Codificación de red Candidata:" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Codificación de red Candidata:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "Cambiar Información." #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Cambiar Información del Amigo" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "Historial de Charlas" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "Elegir archivos anexos" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "Elegir directorios anexos" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "Elegir los archivos para compartir" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "Elegir los directorios para compartir" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Limpiar" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Limpiar buffer" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Limpiar Clave" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Limpiar Tareas" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Limpiar" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Cerrar" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Compatibilidad: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Compatibilidad: Micro$oft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "Completo" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Confirmar Salida" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Contribuciones" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "Costo" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Eliminar" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Eliminar Amigo" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "Eliminar Recursos" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Descendente" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Descripción" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Detectar" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Detectar amigos" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 #, fuzzy msgid "Enclosure." msgstr "Anexo" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Fin de sección IP(v4):" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Ingresar Nueva Clave" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Error" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Evento" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Exportar" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "Fallo la reproducción del archivo, %s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "Fallo al recibir el directorio \"%s\" desde %s!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Fallo al recibir el archivo \"%s\" desde %s!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "Fallo al enviar el directorio \"%s\" a %s!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "Fallo al enviar el archivo \"%s\" a %s!" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Error Fatal!!\n" "No se puede enlazar el puerto TCP/UDP (2425)!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Error Fatal!!\n" "Falló al crear el socket!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Error Fatal!!\n" "No se puede enlazar el puerto TCP/UDP (2425)!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Error Fatal!!\n" "Falló al crear el socket!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "Archivo" #: src/iptux/DialogPeer.cpp:826 #, fuzzy msgid "File received." msgstr "Mensaje recibido" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "La transferencia de archivos no se ha completado.\n" "¿Está seguro que quiere cancelar y salir?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "Nombre de archivo" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "Archivo" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "Administrador de Transferencias" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Filtrar pedido de archivos compartidos" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fopen() archivo \"%s\" fallo!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "Desde" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "Desde:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "Grupo" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Ayuda" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "Equipo" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Equipo: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importar" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Información." #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Información" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Insertar Imagen" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "Es un honor que iptux tenga contribuciones voluntarias de muchos usuarios. " "Sin su ayuda, iptux nunca se pudo haber hecho.\n" "\n" "Especialmente, algunas personas a quien quiero agredecer mucho:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "LiWeijian " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "Cargando el proceso correctamente!" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Miembro" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Mensaje recibido" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 #, fuzzy msgid "Mission Completed!" msgstr "Completo" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() directorio \"%s\" fallo, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "Más Acerca de Iptux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Red" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "Apodo" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Apodo: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Apodo: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "Aceptar" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "Abrir carpeta contenedora" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "Abrir este archivo" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() archivo \"%s\" fallo, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() directorio \"%s\" fallo, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Otros" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Imagen por defecto de amigos:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "Imagen del amigo" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Nombre de grupo del amigo:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Apodo de amigo:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Amigos" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "Amigos En Linea: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "Amigos En Linea: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Fuente:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Clave: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "Compañero" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Personal" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Reproducir" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Por favor Ingrese una dirección IP (IPv4 solamente)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Ingrese una dirección IP (IPv4 solamente):" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Por favor ingrese un nuevo nombre de grupo del amigo!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Por favor ingrese nuevo apodo del amigo!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Ingrese la clave para los archivos compartidos" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Por favor ingrese su grupo!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Por favor ingrese su apodo!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Por favor seleccione una imagen" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Seleccione un archivo para importar" #: src/iptux/dialog.cpp:226 #, fuzzy msgid "Please select a folder to save files." msgstr "Por favor seleccione un archivo de sonido" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Por favor seleccione una foto personal" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "Seleccione una imagen para insertar en la conversación" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Por favor seleccione un archivo de sonido" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Por favor seleccione el directorio de descarga" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Codificación de red Preferida (Ud. debe saber lo que está por hacer si desea " "modificar ésta opción)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Codificación de red Preferida:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Preferencias" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "Progreso" #: src/iptux/HelpDialog.cpp:94 #, fuzzy msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" "Sitio del Proyecto: \n" "http://code.google.com/p/iptux/\n" "\n" "Grupo para Usuarios y Desarrolladores: \n" "https://groups.google.com/group/iptux/\n" "\n" "Ud. puede obtener ayuda desde las páginas del wiki del proyecto.\n" "\n" "Si no encuentra solución en ninguno de los documentos existentes, envíe un " "correo electrónico a iptux@googlegroups.com, muchos usuarios y " "desarrolladores intentaran ayudarlo con sus problemas." #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "Tasa" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "Recibido correctamente el directorio \"%s\" desde %s !" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Recibido correctamente el archivo \"%s\" desde %s !" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Recibido-De: Apodo:%s Usuario:%s Equipo:%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Rechazar" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "Restante" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 #, fuzzy msgid "Remove Selected" msgstr "Selección Reversa" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Repetir: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Pedir Recursos Compartidos" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Selección Reversa" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Guardar datos a un archivo" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Guardar archivo en: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Guardar el historial" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "Buscar Amigos" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Seleccionar Todo" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Seleccionar tipografía" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Enviar" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Enviar Mensaje" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "Envío correcto del directorio \"%s\" a %s !" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Envío correcto del archivo \"%s\" a %s !" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "Difusión" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "Enviado: Apodo:%s Usuario:%s Equipo:%s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "Progreso" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Establecer clave" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "Administrador de Archivos Compartidos" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Firma" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "Firma:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "Tamaño" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Ordenar" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Sonido" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Eventos de Sonidos:" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "Origen" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() archivo \"%s\" fallo, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "Estado" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Detener" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Sistema" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "Codificación del Sistema:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "Codificación del Sistema: %s\n" #: src/iptux/DialogPeer.cpp:189 #, fuzzy, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Charla con %s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Hablar con el grupo %s" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "Tarea" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Terminar Todos" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "Terminar Tarea" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Prueba" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "Una notificación ha sido enviada a %s." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "¡El proceso está a punto de terminar!" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "Hasta" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "Por leer: %u mensajes" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "Para:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Transferencia finalizada" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "Tipo" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Usar la tecla 'Enter' para enviar mensaje" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Usar Blacklist (NO recomendado)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "Usuario" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "Usuario: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "Usuario:%s Equipo:%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Versión: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Contro de Volumen: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Aviso" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Su imagen:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Su grupo:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Su apodo:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Su amigo (%s)[%s]\n" "ha pedido sus recursos compartidos,\n" "¿Está de acuerdo?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "Su amigo no recibió el mensaje. El o ella quizás está desconectado." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Detectar" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "_FAQ" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_Archivo" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Buscar" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "_Ayuda" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "_Ocultar" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "_Mas Acerca de" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "_Preferencias" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Salir" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "Admini_strador de Compartidos" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "_Mostrar" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "_Ordenar" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Herramientas" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "_Transferencias" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "_Actualizar" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "directorio" #: src/iptux/MainWindow.cpp:886 #, fuzzy msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "http://code.google.com/p/iptux/wiki/FAQ_EnglishVersion" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "Error" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "misterioso" #: src/iptux/AnalogFS.cpp:155 #, fuzzy, c-format msgid "opendir on \"%s\" failed: %s" msgstr "Opendir() directorio \"%s\" fallo, %s" #: src/main/iptux.cpp:151 #, fuzzy, c-format msgid "option parsing failed: %s\n" msgstr "Opendir() directorio \"%s\" fallo, %s" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "recibir" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "regular" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "enviar" #: src/iptux/AnalogFS.cpp:141 #, fuzzy, c-format msgid "stat file \"%s\" failed: %s" msgstr "Stat() archivo \"%s\" fallo, %s\n" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "desconocido" #~ msgid "" #~ "\t-h --help\n" #~ "\t\tdisplay this help and exit\n" #~ msgstr "" #~ "\t-h --help\n" #~ "\t\tmuestra esta ayuda y sale\n" #~ msgid "" #~ "\t-v --version\n" #~ "\t\toutput version information and exit\n" #~ msgstr "" #~ "\t-v --version\n" #~ "\t\tmuestra la información de la versión y sale\n" #~ msgid "" #~ "\n" #~ "Can't send an empty message!!" #~ msgstr "" #~ "\n" #~ "No puede enviar un mensaje vacío!!" #~ msgid "Files Receive Management" #~ msgstr "Administrador de Archivos Recibidos" #~ msgid "Free:%s Total:%s" #~ msgstr "Libre:%s Total:%s" #~ msgid "Me" #~ msgstr "Usted" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "Opendir() directorio \"%s\" fallo, %s\n" #~ msgid "Pal's Shared Resources" #~ msgstr "Recursos Compartidos de amigos" #~ msgid "Recv" #~ msgstr "Recv" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "Rmdir() directorio \"%s\" fallo, %s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "Stat() archivo \"%s\" fallo, %s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "El usuario no tiene permisos!\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "Unlink() archivo \"%s\" fallo, %s\n" #~ msgid "What do you want to do?\n" #~ msgstr "¿Qué quiere hacer?\n" #~ msgid "utf-16" #~ msgstr "utf-16" #~ msgid "utf-8" #~ msgstr "utf-8" iptux-0.7.4/po/fr.po000066400000000000000000000726271323207530100142720ustar00rootroot00000000000000# French translation for iptux # Copyright (c) 2010 Rosetta Contributors and Canonical Ltd 2010 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2010. # Fr Cyrille , 2016. msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2016-07-07 21:30+0000\n" "Last-Translator: L'Africain \n" "Language-Team: Moi\n" "Language: fr\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Mot de passe vide !" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Adresse IP(v4) illégale : %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Mot de passe erroné !" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Photo :\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "%s de %s a été envoyé." #: src/iptux/DialogBase.cpp:869 #, fuzzy, c-format msgid "%s Of %s Sent." msgstr "%s de %s a été envoyé." #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "%s à recevoir." #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Mot de passe :" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "iptux : Logiciel de partage pour réseau local\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "…" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "Un logiciel de messagerie en réseau local écrit en GTK+." #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "Accepter" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Mot de passe pour d'accès" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Activer le support de son" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Ajouter" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Ajouter des fichiers" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Ajouter des dossiers" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Ajout de la section IP(v4) :" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "Adresse : %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Adresse : %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Accepter" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Appliquer" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "Ordre croissant" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Joindre un fichier" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Joindre un dossier" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Effacer l'historique de discussion automatiquement" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Cacher automatiquement le panneau une fois connecté" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Ouvrir automatiquement le gestionnaire de transfert" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Ouvrir automatiquement la fenêtre de discussion" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "Soyez CERTAIN de savoir ce que vous faites !" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Compatibilité avec le protocole iptux (DANGEREUX)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Début de la section IP(v4)" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Diffuser" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "Par IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Par Pseudo" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "Impossible de trouver un navigateur web disponible !\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Annuler" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Candidat pour l'encodage réseau" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Encodage réseau suggéré :" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "Modifier l'info." #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Modifier les informations concernant l'ami (e)" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Sauvegarder l'historique de discussion" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 #, fuzzy msgid "Choose enclosure folders" msgstr "Choisissez les dossiers à partager" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "Choisissez les fichiers à partager" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "Choisissez les dossiers à partager" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Effacer" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Vider la mémoire" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Supprimer le mot de passe" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Vider la liste des tâches" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Vider" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Fermer" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Compatibilité : GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Compatibilité : Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "Terminé" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Confirmer la fermeture" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Contributeurs" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "Évaluation" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Supprimer" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Supprimer l'ami(e)" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "Supprimer les ressources" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Ordre décroissant" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Description" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Détecter" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Détecter les ami(e)s" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "Enceinte." #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Fin de la section IP(v4)" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Entrez un nouveau mot de passe" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Erreur" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Événement" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Exporter" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "Échec de la lecture de la sonnerie, %s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "Échec de la réception du dossier \"%s\" de %s !" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Échec de la réception du fichier \"%s\" de %s !" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "Échec de l'envoi du dossier \"%s\" à %s !" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "Échec de l'envoi du fichier \"%s\" à %s !" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Erreur fatale !!\n" "Impossible de se connecter au port TCP/UDP (2425) !\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Erreur fatale !\n" "Erreur d'entrées/sorties!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Erreur fatale !!\n" "Impossible de se connecter au port TCP/UDP (2425) !\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Erreur fatale !\n" "Erreur d'entrées/sorties!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "Fichier" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "Fichier reçu." #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "Fichier à recevoir." #: src/iptux/DialogBase.cpp:719 #, fuzzy msgid "File to send." msgstr "Fichier à recevoir." #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "Le transfert du fichier n'a pas pu être terminé.\n" "Voulez-vous vraiment annuler ou quitter ?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "Nom du fichier" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "Fichier" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "Gestionnaire de partage de fichier" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Filtrer la requête de partage de fichiers" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fl'ouverture() du ficher \"%s\" a échoué !\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "De" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "De :" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "Groupe" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Aide" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "Hôte" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Hôte : %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importer" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Information" #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Information" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Insérer une image" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "C'est un honneur qu'iptux soit le fruit de la contribution de nombreuses " "personnes volontaires. Sans votre aide iptux n'aurait jamais pu faire cela.\n" "\n" "Nous voulons remercier plus particulièrement :\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "LiWeijian " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "Le processus a été charger avec succès !" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Membre" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Message reçu" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "Mission accomplie !" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() dossier \"%s\" a échoué, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "À propos d'Iptux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "Nom" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Réseau" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "Pseudo" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Pseudo : %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Pseudo : %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "OK" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "Ouvrir ce dossier" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "Ouvrir ce fichier" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "L'ouverture() du fichier \"%s\" a échoué, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "L'ouverture() du dossier \\\"%s\\\" a échoué, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Autres" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Photo par défaut de l'ami(e) :" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "Avatar de votre ami(e) :" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Le nom du groupe de votre ami(e) :" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Pseudo du contact :" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Ami(e)s" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "Ami(e)s en ligne : %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "Ami(e)s en ligne : 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Police du panneau :" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Mot de passe : " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 #, fuzzy msgid "PeelName" msgstr "Nom" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "Pair" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Personnel" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Photo" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Lire" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Veuillez entrer une adresse IP (IPv4 seulement) !" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Veuillez entrer une adresse IP (IPv4 seulement) :" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Veuillez entrer le nouveau nom du groupe de votre ami(e) !" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Veuillez saisir le nouveau pseudo du contact" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Veuillez entrer le mot de passe pour le partage de fichiers" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Veuillez entrer le nom de votre groupe !" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Veuillez entrer votre pseudonyme !" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Veuillez sélectionner un avatar" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Veuillez sélectionner un fichier à importer" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "Sélectionnez un dossier où sauver les données." #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Veuillez sélectionner une photo personnelle" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "Veuillez sélectionner une image à insérer" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Veuillez sélectionner un fichier son" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Veuillez sélectionner le dossier de téléchargement" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Préférences de l'encodage réseau (Soyez certains de ce que vous faites si " "vous souhaitez le modifier.)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Préférences de l'encodage réseau :" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Préférences" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "Progression" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "Taux" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "Le dossier \"%s\" de %s a été reçu avec succès !" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Le fichier \"%s\" de %s a été reçu avec succès !" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "Progression de l'envoi." #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "Progression de la réception." #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Reçu de : Pseudo %s Utilisateur :%s Hôte :%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Refuser" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "Restant" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "Supprimer la sélection" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Confirmer : " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Requête de ressources partagées" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Inverser la Sélection" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Sauvegarder les données dans le fichier" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Enregistrer sous " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Sauvegarder l'historique de discussion" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "EnregistrerSous" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "Chercher des ami(e)s" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Tout Sélectionner" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Sélectionner une police de caractères" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Envoyer" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Envoyer un message" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "Le dossier \"%s\" a été envoyé avec succès à %s !" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Le fichier \"%s\" a été envoyé avec succès à %s !" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "Envoi-diffusion" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "Envoyer à : Pseudo %s Utilisateur :%s Hôte :%s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "Progression de l'envoi." #: src/iptux/DialogBase.cpp:724 #, fuzzy msgid "Sending progress." msgstr "Progression de la réception." #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Mettre un mot de passe" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "Gestionnaire de partage de fichier" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Signature" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "Signature :\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "Taille" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Trier" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Son" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Événements sonores" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "Source" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "Statut" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Arrêter" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Système" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "Encodage :" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "Encodage : %s\n" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Communiquer avec %s(%s) IP :%s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Communiquer avec le groupe %s" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "Tâche" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Tout achever" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "Achever la tâche" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Test" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "Le fichier que vous souhaitez ouvrir n'existe pas !" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "La notification a été transmise à %s." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "Le chemin n'existe pas !" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "Le processus est sur le point de quitter !" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "À" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "Lus : %u messages" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "À :" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Transfert terminé" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "Type" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Utilisez la touche 'Entrée' pour envoyer le message" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Utiliser la liste noire (NON recommandé)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "Utilisateur" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "Utilisateur : %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "Utilisateur :%s Hôte :%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Version : %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Contrôle du volume : " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Avertissement" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Votre avatar :" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Le nom de votre groupe :" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Votre pseudonyme :" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Votre ami(e) (%s)[%s]\n" "demande l'accès à vos ressources partagées,\n" "Voulez-vous accepter ?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" "Votre ami(e) n'a pas reçu le paquet. Il ou elle est probablement " "déconnecté(e)." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Détecter" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "_FAQ" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_Fichier" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Rechercher" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "Aid_e" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "Masq_uer" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "_Plus" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "_Préférences" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Quitter" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "_Gestionnaire de partage" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "Mo_ntrer" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "_Trier" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "Ou_tils" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "Trans_mission" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "_Mettre à jour" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT \n" "ButterflyOfFire " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "Dossier" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "iptux" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "mystérieux" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "Reçu" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "normal" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "Envoyer" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "inconnu" #~ msgid "" #~ "\t-h --help\n" #~ "\t\tdisplay this help and exit\n" #~ msgstr "" #~ "\t-h --help\n" #~ "\t\tmontrer l'aide et quitter\n" #~ msgid "" #~ "\t-v --version\n" #~ "\t\toutput version information and exit\n" #~ msgstr "" #~ "\t-v --version\n" #~ "\t\tsortie d'information de version et quitter\n" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "Opendir() dossier \"%s\" a échoué, %s\n" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "Rmdir() dossier \"%s\" a échoué, %s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "Stat() un fichier \"%s\" a échoué, %s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "L'utisateur n'a pas les permissions requises !\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "Échec() de la suppression du fichier \"%s\", %s\n" #~ msgid "What do you want to do?\n" #~ msgstr "Que désirez-vous faire ?\n" #~ msgid "utf-16" #~ msgstr "utf-16" #~ msgid "utf-8" #~ msgstr "utf-8" iptux-0.7.4/po/gl.po000066400000000000000000000556531323207530100142650ustar00rootroot00000000000000# Galician translation for iptux # Copyright (c) 2010 Rosetta Contributors and Canonical Ltd 2010 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2010. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2010-05-03 13:06+0000\n" "Last-Translator: Dario \n" "Language-Team: Galician \n" "Language: gl\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "" #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Automaticamente agochar o panel despois de identificarse" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Difusión" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Candidato de codificación de rede" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Candidato de codificación de rede:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "" #: src/iptux/output.cpp:85 msgid "Error" msgstr "" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/support.cpp:131 #, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/support.cpp:128 #, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/support.cpp:113 #, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/DialogBase.cpp:730 msgid "Files" msgstr "" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "" #: src/iptux/output.cpp:40 msgid "Information" msgstr "" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() directorio \"%s\" fallou, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Rede" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() arquivo \"%s\" fallou, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() directorio \"%s\" fallou, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Outros" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Foto por defecto do teu amigo:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Fonte de panel:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "" #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Persoal" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Por favor introduza o nome do teu grupo!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Por favor intruduza o seu alcume!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Codificación de rede preferido( Deberias saber o que estás a facer antes de " "modificar esto.)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Codificación de rede preferido:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Preferencias" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "" #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Gardar arquivos en: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Sinatura" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Son" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() arquivo \"%s\" fallou, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Sistema" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "" #: src/iptux/output.cpp:63 msgid "Warning" msgstr "" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Unha foto da tua cara:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "O nome do teu grupo:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "O teu alcume:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" "O teu amigo non recibiu o paquetet. El/Ela seguramente estea fora de liña." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "" #: src/iptux/MainWindow.cpp:1851 msgid "iptux Error" msgstr "" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "descoñecido" iptux-0.7.4/po/iptux.pot000066400000000000000000000541311323207530100152060ustar00rootroot00000000000000# SOME DESCRIPTIVE TITLE. # Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , YEAR. # #, fuzzy msgid "" msgstr "" "Project-Id-Version: iptux 0.7.4\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" "Language: \n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=CHARSET\n" "Content-Transfer-Encoding: 8bit\n" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/support.cpp:113 #, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/support.cpp:128 #, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/support.cpp:131 #, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "" #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "" #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "" #: src/iptux/output.cpp:40 msgid "Information" msgstr "" #: src/iptux/output.cpp:63 msgid "Warning" msgstr "" #: src/iptux/output.cpp:85 msgid "Error" msgstr "" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogBase.cpp:730 msgid "Files" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/MainWindow.cpp:1851 msgid "iptux Error" msgstr "" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "" #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" iptux-0.7.4/po/it.po000066400000000000000000000722611323207530100142710ustar00rootroot00000000000000# Italian translation for iptux # Copyright (c) 2013 Rosetta Contributors and Canonical Ltd 2013 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2013. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2013-09-08 09:34+0000\n" "Last-Translator: Wonderfulheart \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" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Password Vuota!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Indirizzo IP(v4) non valido: %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Password Non Corrispondente!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Foto:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "%s di %s Ricevuti." #: src/iptux/DialogBase.cpp:869 #, fuzzy, c-format msgid "%s Of %s Sent." msgstr "%s di %s Ricevuti." #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "%s da Ricevere." #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Password:" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "iptux: Un software per le condivisioni sulla rete LAN\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "Un LAN Messenger basato su GTK+." #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "Accetto" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Password di Accesso" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Attiva il supporto audio" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Aggiungi" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Aggiungi File" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Aggiungi Cartelle" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Aggiunta Sezione IP(v4):" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "Indirizzo: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Indirizzo: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Accetto" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Applica" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "Ascendente" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Allega File" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Allega Cartella" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Pulisci automaticamente la cronologia della chat" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Nascondi automaticamente il pannello dopo l'accesso" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Apri automaticamente Gestione Trasmissione File" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Apri automaticamente la finestra di chat" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "ASSICURATI di sapere cosa stai facendo!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Deve essere compatibile con il protocollo iptux (PERICOLOSO)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Inizio della sezione IP(v4)" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Broadcast" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "Per IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Per Nickname" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "Impossibile trovare alcun web browser disponibile!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Annulla" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Codifica di rete candidata" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Codifica di rete candidata:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "Modifica le Informazioni" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Modifica delle Informazioni del Conoscente" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Salva la cronologia della chat" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 #, fuzzy msgid "Choose enclosure folders" msgstr "Scegli le cartelle da condividere" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "Scegli il file da condividere" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "Scegli le cartelle da condividere" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Cancella" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Cancella il Buffer" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Cancella Password" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Cancella Lista Attività" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Cancella" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Chiudi" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Compatibilità: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Compatibilità: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "Completato" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Conferma l'Uscita" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Collaboratori" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "Costo" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Elimina" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Elimina Conoscenti" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "Elimina le Risorse" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Discendente" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Descrizione" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Rileva" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Rileva conoscenti" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "Allegato." #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Fine della sezione IP(v4)" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Inserisci la Nuova Password" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Errore" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Evento" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Esporta" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "Impossibile riprodurre il tono di prompt, %s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "Ricezione della directory \"%s\" da %s non riuscita!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Ricezione del file \"%s\" da %s non riuscita!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "Invio della directory \"%s\" a %s non riuscito!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "Invio del file \"%s\" a %s non riuscito!" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Errore Fatale!!\n" "Ascolto sulla porta TCP/UDP (2425) non riuscito!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Errore Fatale!!\n" "Impossibile creare il nuovo socket!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Errore Fatale!!\n" "Ascolto sulla porta TCP/UDP (2425) non riuscito!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Errore Fatale!!\n" "Impossibile creare il nuovo socket!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "File" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "File ricevuto." #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "File da ricevere." #: src/iptux/DialogBase.cpp:719 #, fuzzy msgid "File to send." msgstr "File da ricevere." #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "Il trasferimento del file non è stato completato.\n" "Sei sicuro di voler annullare ed interrompere?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "Nome del file" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "File" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "Gestione Trasmissione File" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Filtra la richiesta di condivisione dei file" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fopen() file \"%s\" non riuscito!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "Da" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "Da:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "Gruppo" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Aiuto" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "Host" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Host: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importa" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Informazioni" #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Informazioni" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Inserisci un'Immagine" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "È un onore che iptux abbia collaborazioni volontarie da molte persone. Senza " "il tuo aiuto, iptux non potrebbe mai farcela.\n" "\n" "In particolare, ecco alcune persone che vorremmo ringraziare molto:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "LiWeijian " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "Processo caricato con successo!" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Membro" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Messaggio ricevuto" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "Missione Completata!" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() directory \"%s\" non riuscito, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "Maggiori informazioni su Iptux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "Nome" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Rete" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "Nickname" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Nickname: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Nickname: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "OK" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "Apri cartella in cui è contenuto" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "Apri Questo File" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() file \"%s\" non riuscito, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() directory \"%s\" non riuscito, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Altri" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Immagine predefinita del volto del conoscente:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "Immagine del volto del conoscente:" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Nome del gruppo di conoscenti:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Nickname del conoscente:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Conoscenti" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "Conoscenti Collegati: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "Conoscenti Collegati: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Pannello dei font:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Password: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 #, fuzzy msgid "PeelName" msgstr "Nome" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "Nodo" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Dati Personali" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Riproduci" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Per favore, inserisci un indirizzo IP (solo IPv4)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Per favore, inserisci un indirizzo IP (solo IPv4):" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Per favore, inserisci il nome del nuovo gruppo di conoscenti!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Per favore, inserisci il nuovo nickname del conoscente!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Per favore, prima inserisci la password per la condivisione dei file" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Per favore, inserisci Il nome del tuo gruppo!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Per favore, inserisci il tuo Nickname!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Per favore, scegli un'immagine per il volto" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Per favore, scegli un file per importare i dati" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "Per favore, scegli una cartella dove salvare i file." #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Per favore, scegli una foto personale" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "Per favore, seleziona un'immagine da inserire nel buffer" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Per favore, scegli un file audio" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Per favore, scegli una cartella per il download" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Codifica delle preferenze di rete (Dovresti essere consapevole di ciò che " "stai facendo se volessi modificarla)." #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Codifica delle preferenze di rete:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Preferenze" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "Avanzamento" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "Velocità" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "Ricezione della directory \"%s\" da %s con successo!" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Ricezione del file \"%s\" da %s con successo!" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "Avanzamento Ricezione." #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "Avanzamento ricezione." #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Ricevuto da: Nickname:%s Utente:%s Host:%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Rifiuto" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "Rimanenti" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "Rimuovi i Selezionati" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Ripeti: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Richiedi le Risorse Condivise" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Inverti la Selezione" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Salva i dati nel file" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Salva file in: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Salva la cronologia della chat" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "Salva come" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "Cerca Conoscenti" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Seleziona Tutto" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Scegli il Font" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Invia" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Invia Messaggio" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "La directory \"%s\" è stata inviata con successo a %s!" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Il file \"%s\" è stato inviato con successo a %s!" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "Invio Broadcast" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "Invia a: Nickname:%s Utente:%s Host:%s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "Avanzamento Ricezione." #: src/iptux/DialogBase.cpp:724 #, fuzzy msgid "Sending progress." msgstr "Avanzamento ricezione." #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Imposta Password" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "Gestione File Condivisi" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Firma" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "Firma:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "Dimensione" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Ordinamento" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Audio" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Evento Audio" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "Sorgente" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() file \"%s\" non riuscito, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "Stato" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Ferma" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Sistema" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "Sistema di codifica:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "Sistema di codifica: %s\n" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Conversazione con %s(%s) IP:%s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Conversazione con il gruppo %s" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "Attività" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Termina Tutto" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "Termina Attività" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Test" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "Il file che vuoi aprire non esiste!" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "La notifica è stata inviata a %s." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "Il percorso che vuoi aprire non esiste!" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "Il processo è in procinto di interruzione!" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "A" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "Da leggere: %u messaggi" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "A:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Trasferimento terminato" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "Tipo" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Usa il tasto 'Invio' per inviare il messaggio" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Usa la Blacklist (NON raccomandato)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "Utente" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "Utente: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "Utente:%s Host:%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Versione: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Controllo Volume: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Avviso" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Immagine del tuo volto:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Il nome del tuo gruppo:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Il tuo Nickname:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Il tuo conoscente (%s)[%s]\n" "ha richiesto di accedere alle tue risorse condivise,\n" "Sei d'accordo?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" "Il tuo conoscente non ha ricevuto i dati. Lei o lui potrebbe essere offline." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Rileva" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "_FAQ" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_File" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Trova" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "_Aiuto" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "_Nascondi" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "Altre _Info" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "_Preferenze" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Esci" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "_Gestione Condivisioni" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "_Mostra" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "_Ordinamento" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Strumenti" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "Tras_missione" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "Aggio_rna" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT \n" "Wonderfulheart " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "directory" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "iptux" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "misterioso" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "ricezione" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "regolare" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "invia" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "sconosciuto" #~ msgid "" #~ "\t-h --help\n" #~ "\t\tdisplay this help and exit\n" #~ msgstr "" #~ "\t-h --help\n" #~ "\t\tvisualizza questo aiuto ed esce\n" #~ msgid "" #~ "\t-v --version\n" #~ "\t\toutput version information and exit\n" #~ msgstr "" #~ "\t-v --version\n" #~ "\t\trestituisce l'informazione di versione ed esce\n" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "Opendir() directory \"%s\" non riuscito, %s\n" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "Rmdir() directory \"%s\" non riuscito, %s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "Stat() file \"%s\" non riuscito, %s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "L'utente non è privilegiato!\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "Unlink() file \"%s\" non riuscito, %s\n" #~ msgid "What do you want to do?\n" #~ msgstr "Cosa vuoi fare?\n" #~ msgid "utf-16" #~ msgstr "utf-16" #~ msgid "utf-8" #~ msgstr "utf-8" iptux-0.7.4/po/lb.po000066400000000000000000000561651323207530100142570ustar00rootroot00000000000000# Luxembourgish translation for iptux # Copyright (c) 2010 Rosetta Contributors and Canonical Ltd 2010 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2010. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2010-08-30 21:09+0000\n" "Last-Translator: n0a3n \n" "Language-Team: Luxembourgish \n" "Language: \n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "" #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "Fehler" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Den Toun support activeieren" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Dobäisetzen" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Fichier attacheieren" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Dossier attacheieren" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Automatech Chat history laeschen" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Automatech verstopt den Panel no dem aloggen" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Noriichten" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Ofbriechen" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Chat historie speicheren" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Eidelmaachen" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Buffer eidelmaachen" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Zoumaachen" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Läschen" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Ofsteigend" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Git eent neid Passwuert an" #: src/iptux/output.cpp:85 msgid "Error" msgstr "" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Evenement" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Exportéieren" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/support.cpp:131 #, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/support.cpp:128 #, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" #: src/iptux/support.cpp:113 #, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "_Fichier" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "vun" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "vun" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importéieren" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Info." #: src/iptux/output.cpp:40 msgid "Information" msgstr "" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Foto integreieren" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Member" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Noriicht empfaang" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Netzwierk" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Aner" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Passwuert: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Perséinlech" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Ofspillen" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Git Weg Aeren Gruppennum an" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Weg git Aeren Spetznum an" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Weg wielt den Eroofluerddossier aus" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Astellungen" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Refuseieren" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "nachengkeier " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Save daten an een fichier" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Fichier speicheren enneret " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Chat historie speicheren" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Alles auswielen" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Schrëft auswielen" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Fortschécken" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Ënnerschrëft" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Sortéieren" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Toun" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Stop" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "System" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Test" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "fier" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "fier" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Den transfer as faerdech" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Versioun %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "" #: src/iptux/output.cpp:63 msgid "Warning" msgstr "" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Dain Gesiicht am Bild" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Aeren Gruppennum" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Aere Spetznum" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_Fichier" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Geschir" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "" #: src/iptux/MainWindow.cpp:1851 msgid "iptux Error" msgstr "" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "onbekannt" #~ msgid "The user is not privileged!\n" #~ msgstr "Den User huet d'Rechter net\n" iptux-0.7.4/po/pl.po000066400000000000000000000721141323207530100142650ustar00rootroot00000000000000# Polish translation for iptux # Copyright (c) 2010 Rosetta Contributors and Canonical Ltd 2010 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2010. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2010-07-29 13:29+0000\n" "Last-Translator: Twojwujaszek \n" "Language-Team: Polish \n" "Language: pl\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2010-07-29 14:36+0000\n" "X-Generator: Launchpad (build Unknown)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Puste Hasło!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Nieprawidłowy adres IP(v4): %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Niezgodne Hasło!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "Zdjęcie:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Hasło:" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "iptux: Program do komunikacji w sieciach LAN\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "Komunikator LAN oparty na bibliotece GTK+" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "Akceptuj" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Hasło dostępu" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Aktywuj dźwięk" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Dodaj" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "Dodaj Pliki" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "Dodaj Katalogi" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Dodaj sekcję IP(v4)" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "Addres: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "Addres: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Akceptuj" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "Zastosuj" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "Rosnąco" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "Dołącz Plik" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "Dołącz Folder" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Automatycznie czyść historię rozmowy" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Automatycznie ukryj panel po zalogowaniu" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Automatycznie otwórz Narzędzie Transmisji Plików" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Automatyczne otwieranie okna rozmowy" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "Upewnij się, że WIESZ CO ROBISZ!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Zgodność z protokołem iptux (niebezpieczne)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Początek sekcji IP(v4)" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Adres rozgłoszeniowy" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "Wg IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Wg Nazwy" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "Nie można znaleźć żadnej dostępnej przeglądarki internetowej!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Anuluj" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Kandydat kodowania sieci" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Kandydat kodowania sieci:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "Zmień Info." #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "Zmień Informacje o znajomym" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Zapisz historię rozmowy" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 #, fuzzy msgid "Choose enclosure folders" msgstr "Wybierz katalogi do współdzielenia" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "Wybierz pliki do współdzielenia" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "Wybierz katalogi do współdzielenia" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Wyczyść" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Czyść Bufor" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "Wyczyśc Hasło" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "Wyczyśc Listę Zadań" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Wyczyść" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "Zamknij" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "Kompatybilność: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "Kompatybilność: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "Zakończone" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Potwierdz zamknięcie" #: src/iptux/HelpDialog.cpp:92 #, fuzzy msgid "Contributors" msgstr "Uczestnicy" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "Koszt" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Usuń" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "Usuń Kontakt" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "Usuń Zasoby" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "Malejąco" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Opis" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Wykrywanie" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Szukaj znajomych" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Koniec sekcji IP(v4)" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Wpisz Nowe Hasło" #: src/iptux/output.cpp:85 msgid "Error" msgstr "Błąd" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Zdarzenie" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Eksport" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "Nie udało się odtworzyć dźwięku polecenia,% s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "Błąd odbioru katalogu \"%s\" od %s!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "Błąd odbioru pliku \"%s\" od %s!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "Błąd wysyłania katalogu \"%s\" do %s!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "Błąd wysyłania pliku \"%s\" do %s!" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Błąd krytyczny!\n" "Nie można połączyć się z portem TCP/UDP (2425)!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Błąd Krytyczny!!\n" "Nie można utworzyć nowego gniazda sieciowego!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Błąd krytyczny!\n" "Nie można połączyć się z portem TCP/UDP (2425)!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Błąd Krytyczny!!\n" "Nie można utworzyć nowego gniazda sieciowego!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "Plik" #: src/iptux/DialogPeer.cpp:826 #, fuzzy msgid "File received." msgstr "Odebrano wiadomość" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "Przesyłanie plików nie zostało zakończone.\n" "Czy na pewno anulować, i wyjść?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "Nazwa pliku" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "Plik" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "Narzędzie Transmisji Plików" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Filtruj żądanie współdzielenia plików" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fopen() plik \"%s\" błąd!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "Od" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "Od:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "Grupa" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "Pomoc" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "Host" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "Host: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Import" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "Info." #: src/iptux/output.cpp:40 #, fuzzy msgid "Information" msgstr "Infomacje" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "Wstaw obrazek" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "To zaszczyt, że iptux został wspóltworzony przez wiele osób. Bez Twojej " "pomocy, iptux nigdy by nie powstał.\n" "\n" "Oto kilka osób, którym chcielibyśmy szczególnie podziękować:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "LiWeijian " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "Proces załadowany pomyślnie" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Członek" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Odebrano wiadomość" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 #, fuzzy msgid "Mission Completed!" msgstr "Zakończone" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() katalog \"%s\" błąd, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "Więcej o Iptux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Sieć" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "Nick" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "Nick: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "Nick: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "OK" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() plik \"%s\" błąd, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() katalog \"%s\" błąd, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Inne" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Domyślny avatar kontaktów:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "Avatar Znajomego:" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "Nazwa grupy Znajomego" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "Nick Znajomego:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Znajomi" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "Znajomi Online: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "Znajomych Online: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Czcionka panelu:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Hasło: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "Partner" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Osobiste" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Zdjęcie" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Odtwórz" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Wpisz adres IP (Tylko IPv4)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Wpisz adres IP (Tylko IPv4):" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "Wpisz nową nazwę grupy znajomego!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "Wpisz nowy nick znajomego!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Proszę wpisać hasło dla udostępnionych plików" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Proszę wpisać swoją nazwę grupy!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Proszę wpisać swój nick" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Wybierz avatar" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Wybierz plik do zaimportowania danych" #: src/iptux/dialog.cpp:226 #, fuzzy msgid "Please select a folder to save files." msgstr "Wybierz plik dźwiękowy" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Wybierz osobiste zdjęcie" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "Wybierz zdjęcie, aby wstawić do bufora" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Wybierz plik dźwiękowy" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Wybierz folder pobierania" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Kandydat kodowania sieci (Zmień tylko gdy jesteś świadomy tego co robisz.)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Ustawienia kodowania sieci:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Preferencje" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "Postęp" #: src/iptux/HelpDialog.cpp:94 #, fuzzy msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" "Strona Domowa Projektu: \n" "http://code.google.com/p/iptux/\n" "\n" "Grupa użytkowników i programistów: \n" "https://groups.google.com/group/iptux/\n" "\n" "Pamiętaj, że możesz uzyskać pomoc w ramach projektu wiki.\n" "\n" "Jeśli nie znajdziesz rozwiązania w żadnym z istniejących dokumentów, prosimy " "o e-mail na adres iptux@googlegroups.com, wielu użytkowników i deweloperów " "otrzymuje tam pomoc w swoich problemach." #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "Szybkość" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "Odbiór katalogu \"%s\" od %s zakończony powodzeniem!" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "Odbiór pliku \"%s\" od %s zakończony powodzeniem!" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "Otrzymane od: Nick:%s Użytkownik:%s Host:%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Odrzuć" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "Pozostało" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 #, fuzzy msgid "Remove Selected" msgstr "Wybór zwrotu" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Powtórz: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Zapytanie o Udostępnione Zasoby" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Wybór zwrotu" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Zapisz dane do pliku" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Zapisz pliki do: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Zapisz historię rozmowy" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "Szukaj Znajomych" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Zaznacz wszystko" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Wybierz czcionkę" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Wyślij" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "Wyślij wiadomość" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "Wysyłanie katalogu \"%s\" do %s zakończone powodzeniem!" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "Wysyłanie pliku \"%s\" do %s zakończone powodzeniem!" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "Wysłane-Rozgłoszenie" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "Wysłane do: Nick:%s Użytkownik:%s Host:%s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "Postęp" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "Ustaw hasło" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "Zarządzanie Współdzieleniem Plików" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Sygnatura" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "Sygnatura:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "Rozmiar" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Sortuj" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Dźwięk" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Zdarzenia dźwiękowe" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "Źródło" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() plik \"%s\" błąd, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "Stan" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Stop" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "System" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "Kodowanie Systemu:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "Kodowanie Systemu: %s\n" #: src/iptux/DialogPeer.cpp:189 #, fuzzy, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Rozmawiaj z %s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Rozmawiaj z grupą %s" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "Zadanie" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "Zakończ Wszystkie" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "Zakończ Zadanie" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Test" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "Zgłoszenie zostało wysłane do %s." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "Proces zostanie zakończony" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "Do" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "Do przeczytania: %u wiadomości" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "Do:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Transfer zakończony" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "Typ" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Używaj 'Enter' by wysłać wiadomość" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Używaj Blacklisty ( NIE zalecane)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "Użytkownik" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "Użytkownik: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "Użytkownik:%s Host:%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "Wersja: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Poziom głośności: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "Ostrzeżenie" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Twój avatar:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Twoja nazwa grupy" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Twój nick:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Twój znajomy (%s)[%s]\n" ",pyta o Twoje Udostępnione Zasoby\n" "Zgadzasz się?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "Twój znajomy nie otrzymał pakietu. Być może jest niedostępny." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "_Wykryj" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "_FAQ" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "_Plik" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "_Znajdź" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "_Pomoc" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "_Ukryj" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "_Więcej" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "_Preferencje" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "_Zakończ" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "_Zarządzanie Współdzieleniem Plików i Folderów" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "_Pokaż" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "_Sortuj" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Narzędzia" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "_Transmisja" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "_Aktualizuj" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "Tybek " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "katalog" #: src/iptux/MainWindow.cpp:886 #, fuzzy msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "http://code.google.com/p/iptux/wiki/FAQ_EnglishVersion" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "iptux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "Błąd" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "tajemniczy" #: src/iptux/AnalogFS.cpp:155 #, fuzzy, c-format msgid "opendir on \"%s\" failed: %s" msgstr "Opendir() katalog \"%s\" błąd, %s" #: src/main/iptux.cpp:151 #, fuzzy, c-format msgid "option parsing failed: %s\n" msgstr "Opendir() katalog \"%s\" błąd, %s" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "odbiór" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "regularny" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "Wyślij" #: src/iptux/AnalogFS.cpp:141 #, fuzzy, c-format msgid "stat file \"%s\" failed: %s" msgstr "Stat() plik \"%s\" błąd, %s\n" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "nieznany" #~ msgid "" #~ "\t-h --help\n" #~ "\t\tdisplay this help and exit\n" #~ msgstr "" #~ "\t-h --help\n" #~ "\t\twyświetlenie pomocy i zakończenie\n" #~ msgid "" #~ "\t-v --version\n" #~ "\t\toutput version information and exit\n" #~ msgstr "" #~ "\t-v --version\n" #~ "\t\twyświetlenie informacji o wersji i zakończenie\n" #~ msgid "Files Receive Management" #~ msgstr "Zarządzanie Odbiorem Plików" #~ msgid "Free:%s Total:%s" #~ msgstr "Pozostało:%s Wszystko:%s" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "Opendir() katalog \"%s\" błąd, %s\n" #~ msgid "Pal's Shared Resources" #~ msgstr "Współdzielone Zasoby Znajomych" #~ msgid "Recv" #~ msgstr "Odebrane" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "Rmdir() katalog \"%s\" błąd, %s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "Stat() plik \"%s\" błąd, %s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "Użytkownik nie ma uprawnień!\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "Unlink() plik \"%s\" błąd, %s\n" #~ msgid "What do you want to do?\n" #~ msgstr "Co chcesz robić?\n" #~ msgid "utf-16" #~ msgstr "utf-16" #~ msgid "utf-8" #~ msgstr "utf-8" iptux-0.7.4/po/pt_BR.po000066400000000000000000000615521323207530100146640ustar00rootroot00000000000000# Brazilian Portuguese translation for iptux # Copyright (c) 2011 Rosetta Contributors and Canonical Ltd 2011 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2011. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2016-11-01 13:56+0000\n" "Last-Translator: EquipeLinux \n" "Language-Team: Brazilian Portuguese \n" "Language: pt_BR\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "Senha Vazia!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Endereço IP(v4): %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "Senhas não conferem!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]Senha:" #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "<ÊRRO>" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "Senha de Acesso" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Ativa o suporte a som" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Adicionar" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "Seção IP(v4) adicionada:" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "Concordo" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Automaticamente limpa o histórico de conversa" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Automaticamente esconde o painel depois da entrada" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Automaticamente abre o Gerenciamento de Transmissão de Arquivo" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Automaticamente abre o diálogo de conversa" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "Início da seção IP(v4)" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Difusão" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "Por Apelido" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "Cancela" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Codificação da rede candidata" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "Codificação da rede candidata:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Salva o histórico da conversa" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Limpar" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "Limpar Buffer" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "Limpa Tudo" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "Confirme Saída" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Deletar" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Descrição" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "Detectar" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "Detetar amigos" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "Fim da seção (IPv4)" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "Entre uma Nova Senha" #: src/iptux/output.cpp:85 msgid "Error" msgstr "" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "Evento" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Exportar" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Êrro Fatal!!\n" "Falhou em criar novo socket!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Êrro Fatal!!\n" "Falhou em criar novo socket!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Êrro Fatal!!\n" "Falhou em criar novo socket!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Êrro Fatal!!\n" "Falhou em criar novo socket!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "A transferência do arquivo não foi completada.\n" "Você está certo que quer cancelar e sair?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/DialogBase.cpp:730 msgid "Files" msgstr "" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Filtra a requisição de compartilhamento de arquivos" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "Fopen() arquivo \"%s\" falhou!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "De" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "De:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Importar" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "" #: src/iptux/output.cpp:40 msgid "Information" msgstr "" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "Membro" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "Mensagem recebida" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "Mkdir() diretório \"%s\" fallhou, %s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Rede" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "Open() arquivo \"%s\" falhou, %s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "Opendir() diretório \"%s\" falhou, %s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Outros" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Foto da Face do amigo(a):" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "Amigos(as)" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Caractere do Painel:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "Senha : " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Pessoal" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Foto" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "Reproduzir" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Favor entrar um endereço IP (IPv4 somente)" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Favor entrar endereço IP (IPv4 somente)" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "Favor entrar a senha para arquivos compartilhados atrás" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Favor entrar seu nome de grupo!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Favor entrar seu apelido!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "Favor selecionar uma imagem de capa" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "Favor selecionar um arquivo para importar dados" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "Favor escolher uma pasta para salvar arquivos." #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "Favor selecionar uma foto pessoal" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "Favor escolher um arquivo de som" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "Favor escolher pasta de descarga" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Codificação da rede preferida (Você dese estar ciente do que está fazendo se " "quer modificar isto)." #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Codificação da rede preferida:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Preferências" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "Recuso" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "Repita: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "Compartilhamento de Recursos requisitado" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "Seleção reversa" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "Salva dados para arquivo" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Salvar arquivos em: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Salva o histórico da conversa" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "Selecionar tudo" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "Selecionar caractere" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "Enviar" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Assinatura" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "Ordenar" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Som" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Som de Evento" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "Stat64() arquivo \"%s\" falhou, %s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Pare" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Sistema" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "Converse com o grupo %s" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Teste" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "A notificação foi enviada para %s." #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "Para" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "Para:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "Transferência encerrada" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Use a tecla 'Enter' para enviar mensagem" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Use a ListaNegra (não recomendado)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Controle de Volume: " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "A Foto de sua Face" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Seu nome de Grupo" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Seu apelido:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "Seu(ua) amigo(a) (%s)[%s]\n" "está requisitando obter seus recursos compartilhados,\n" "Você aceita?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "" "Seu(ua) amigo(a) não recebeu o pacote. Ele, ou ela, talvez esteja fora da " "rede.\r\n" "Your pal didn't receive the packet. He or she is offline maybe." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "_Ferramentas" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "" #: src/iptux/MainWindow.cpp:1851 msgid "iptux Error" msgstr "" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "desconhecido(a)" iptux-0.7.4/po/ru.po000066400000000000000000000612631323207530100143030ustar00rootroot00000000000000# Russian translation for iptux # Copyright (c) 2014 Rosetta Contributors and Canonical Ltd 2014 # This file is distributed under the same license as the iptux package. # FIRST AUTHOR , 2014. # msgid "" msgstr "" "Project-Id-Version: iptux\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2014-03-10 01:03+0000\n" "Last-Translator: EvgeniusDragon \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" "X-Launchpad-Export-Date: 2018-01-24 12:00+0000\n" "X-Generator: Launchpad (build 18532)\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "Запрещенный адрес IP(v4): %s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "" #: src/main/iptux.cpp:147 #, fuzzy msgid "- A software for sharing in LAN" msgstr "IPTux - приложение для обмена файлов и сообщений в Локальной сети.\n" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "" #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "Включение поддержки звука" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "Добавить" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "Автоматическая очистка истории сообщений" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "Автоматически сворачивать панель после входа" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "Автоматически открывать управление передачей файла" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "Автоматически открывать диалог беседы" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "Совместимость с протоколом iptux (Не безопасно!)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "Вещание" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "По IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "Дополнительная кодировка" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "" #: src/iptux/DialogBase.cpp:301 #, fuzzy msgid "Chat History" msgstr "Сохранять историю сообщений" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "Очистить" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "Удалить" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "Описание" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "" #: src/iptux/output.cpp:85 msgid "Error" msgstr "" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "Экспорт" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Ошибка!!!\n" "Не удалось создать новый сокет!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "Ошибка!!!\n" "Не удалось создать новый сокет!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "Ошибка!!!\n" "Не удалось создать новый сокет!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "Ошибка!!!\n" "Не удалось создать новый сокет!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "" #: src/iptux/DialogBase.cpp:730 msgid "Files" msgstr "" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "Фильтр запросов на обмен файлами" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "От:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "Импорт" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "" #: src/iptux/output.cpp:40 msgid "Information" msgstr "" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "" #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "Узнать больше о IPTux" #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "Сеть" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "Прочие" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "Аватар собеседника по умолчанию:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "Панель шрифтов:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "" #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "Личные" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "Фото" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "Введите IP-адрес (только IPv4)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "Введите IP-адрес (только IPv4)" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "Пожалуйста, введите название Вашей группы!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "Пожалуйста, введите ник!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "" "Стандартная кодировка (Вы должны быть уверенны перед тем как изменить это " "значение)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "Стандартная кодировка" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "Параметры" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "" #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "Сохранять файлы в: " #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "Сохранять историю сообщений" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "Подпись" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "Звук" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "Звуковые оповещения" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "Стоп" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "Система" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "Разговаривать с %s(%s) IP:%s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "Проверка" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "К:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "Отправка сообщения по нажатию \"Enter\"" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "Использовать черный список (НЕ рекомендуется)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "Регулятор громкости " #: src/iptux/output.cpp:63 msgid "Warning" msgstr "" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "Аватар:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "Название Вашей группы:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "Ваш ник:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "Ваш собеседник не получил сообщение. Возможно он(она) сейчас вне сети." #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "IPTux" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "IPTux" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "неизвестный" iptux-0.7.4/po/zh_CN.po000066400000000000000000000667501323207530100146640ustar00rootroot00000000000000# Translation of iptux to Chinese (simplified) # Copyright (C) 2009 THE IPTUX'S COPYRIGHT HOLDER # This file is distributed under the same license as the iptux package. # Jally , 2008, 2009. # ManPT , 2009. # msgid "" msgstr "" "Project-Id-Version: iptux 0.6.3\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2010-03-26 00:20+0800\n" "Last-Translator: NightSharp \n" "Language: zh_CN\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Generator: Lokalize 0.3\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "密码为空!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "非法的IP(v4)地址:%s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "密码不一致!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "个人形象:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "已接收 %s,总共 %s " #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "已传输 %s,总共 %s " #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "%s 等待传输" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "%s 等待接收" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]密码: " #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "- 一款用于在局域网内共享文件的软件" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "<错误>" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "一个基于GTK+的局域网通信工具" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "接受" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "获取密码" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "启动声音支持" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "增添" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "增添文件" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "增添目录" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "已添加的IP(v4)网段:" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "地址: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "地址: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "允许" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "应用" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "升序" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "增添文件" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "增添目录" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "自动清空聊天历史记录" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "程序启动之后自动隐藏面板" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "自动打开文件传输管理器" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "自动打开聊天窗口" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "你最好明白你到底在做些什么!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "兼容 iptux 扩展协议(危险)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "IP(v4)网络段起始点" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "广播" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "按 IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "按昵称" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "无法找到可用的浏览器!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "取消" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "候选网络编码" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "候选网络编码:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "更改信息" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "更改好友信息" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "聊天记录" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "选择文件附件" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "选择文件夹附件" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "选择共享文件" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "选择共享文件夹" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "清空" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "清空缓冲" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "清除密码" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "清理任务" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "清空" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "关闭" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "兼容性: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "兼容性: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "已完成" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "确认退出" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "贡献者" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "花费时间" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "删除" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "删除好友" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "删除资源" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "降序" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "描述" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "详情" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "探测" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "探测好友" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "目录" #: src/iptux/DialogPeer.cpp:735 msgid "Enclosure." msgstr "附件" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "IP(v4)网络段终止点" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "输入一个新的密码" #: src/iptux/output.cpp:85 msgid "Error" msgstr "错误" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "事件" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "导出" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "播放提示音失败,%s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "接收文件夹\"%s\"(来自%s)失败!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "接收文件\"%s\"(来自%s)失败!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "发送文件夹\"%s\"到%s失败!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "发送文件\"%s\"到%s失败!" #: src/iptux/support.cpp:131 #, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "致命错误!!\n" "绑定TCP/UDP端口(%d)失败!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "致命错误!!\n" "创建新的套接口失败!\n" "%s" #: src/iptux/support.cpp:128 #, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "致命错误!!绑定TCP/UDP端口(%d)失败!\n" "%s" #: src/iptux/support.cpp:113 #, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "致命错误!!\n" "创建新的套接口失败!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "文件" #: src/iptux/DialogPeer.cpp:826 msgid "File received." msgstr "已接收的文件" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "等待接收的文件" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "等待传输的文件" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "文件传输尚未完成。\n" "你确定要取消任务并退出吗?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "文件名" #: src/iptux/DialogBase.cpp:730 msgid "Files" msgstr "文件" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "文件传输管理器" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "过滤好友对共享文件的请求" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "打开文件\"%s\"失败!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "起始" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "起始:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "组名" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "帮助" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "主机" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "主机: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "导入" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "信息" #: src/iptux/output.cpp:40 msgid "Information" msgstr "信息" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "插入图片" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" "很荣幸有很多人们自发为iptux项目作出了贡献。没有你们的帮助,iptux不可能做到现" "在这样。\n" "\n" "特别地,这里有些人我们想要表示高度感谢:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "Jally " #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "牛牛 " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "进程加载成功!" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "ManPT " #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "成员" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "收到消息" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 msgid "Mission Completed!" msgstr "任务完成" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "创建文件夹\"%s\"失败,%s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "更多..." #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "名称" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "网络" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "昵称" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "昵称: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "昵称: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "确定" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "打开所在文件夹" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "打开文件" # "Language-Team: Chinese (simplified) \n" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "打开文件\"%s\"失败,%s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "打开文件夹\"%s\"失败,%s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "其他" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "好友默认头像:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "好友头像:" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "好友组名:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "好友昵称:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "好友" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "在线好友: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "在线好友: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "面板字体:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "密码: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "路径" #: src/iptux/DialogBase.cpp:780 #, fuzzy msgid "PeelName" msgstr "名称" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "好友" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "个人" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "个人形象" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "播放" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "请输入IP地址(限IPv4格式)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "请输入IP地址(限IPv4格式):" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "请输入好友的新组名!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "请输入好友的新昵称!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "请输入获取共享文件的密码" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "请输入您的组名!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "请输入您的昵称!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "请选择一个头像图片" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "请选择导入数据的文件" #: src/iptux/dialog.cpp:226 msgid "Please select a folder to save files." msgstr "请选择一个文件夹来保存文件" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "请选择个人形象照片" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "请选择插入缓冲区的图片" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "请选择一个声音文件" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "请选择下载文件夹" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "首选网络编码(如果你想要修改它,那么你必须明白你正在做什么。)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "首选网络编码:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "参数选择" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "进度" #: src/iptux/HelpDialog.cpp:94 msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" "项目主页: \n" "https://github.com/iptux-src/iptux\n" "\n" "用户邮件组: \n" "https://groups.google.com/group/iptux/\n" "\n" "遇到问题时,麻烦留意一下项目Wiki页面,会得到不少帮助信息。\n" "\n" "如果仍然找不到解决的办法,欢迎发信到邮件组iptux@googlegroups.com,我们会乐意" "帮助你解决问题。" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "速率" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "接收文件夹\"%s\"(来自%s)成功!" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "接收文件\"%s\"(来自%s)成功!" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "接收进度" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "接收进度" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "来自: 昵称:%s 用户:%s 主机:%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "拒绝" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "剩余时间" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 msgid "Remove Selected" msgstr "移除选中项" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "重复: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "请求共享资源" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "反选" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "保存数据到文件" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "保存文件到:" #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "保存聊天历史" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "另存为" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "搜索好友" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "全选" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "选择字体" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "发送" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "发送消息" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "发送文件夹\"%s\"到%s失败!" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "发送文件\"%s\"到%s成功!" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "发送广播" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "发往: 昵称:%s 用户:%s 主机:%s" #: src/iptux/DialogBase.cpp:866 msgid "Sending Progress." msgstr "传输进度" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "传输进度" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "设置密码" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "共享文件管理器" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "个性签名" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "个性签名:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "大小" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "排序" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "声音" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "声音事件" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "来源" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "获取文件\"%s\"状态失败,%s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "状态" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "停止" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "系统" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "系统编码:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "系统编码: %s\n" #: src/iptux/DialogPeer.cpp:189 #, c-format msgid "Talk with %s(%s) IP:%s" msgstr "与 %s(%s) 对话 IP地址: %s" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "与%s组对话" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "任务" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "终止所有" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "终止任务" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "测试" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "你想打开的文件不存在!" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "通知已经发送到%s。" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "你想打开的路径不存在" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "进程即将退出!" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "终止" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "未读消息: %u条" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "终止:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "传输完成" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "类型" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "使用Enter键发送消息" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "开启黑名单处理方案(不推荐)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "用户" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "用户: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "用户:%s 主机:%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "版本: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "音量控制:" #: src/iptux/output.cpp:63 msgid "Warning" msgstr "警告" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "您的头像:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "您的组名:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "您的昵称:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "您的好友(%s)[%s]\n" "请求获取您的共享资源,\n" "是否允许?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "你的好友没有接收到此数据包,他可能已经下线。" #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "探测(_D)" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "FAQ(_F)" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "文件(_F)" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "查找(_F)" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "帮助(_H)" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "隐藏(_H)" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "更多(_M)" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "首选项(_P)" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "退出(_Q)" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "共享管理器(_S)" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "显示(_S)" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "排序(_S)" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "工具(_T)" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "传输管理器(_T)" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "刷新(_U)" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "文件夹" #: src/iptux/MainWindow.cpp:886 msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "http://code.google.com/p/iptux/wiki/FAQ" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "信使(iptux)" #: src/iptux/MainWindow.cpp:1851 msgid "iptux Error" msgstr "iptux 错误" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "神秘来客" #: src/iptux/AnalogFS.cpp:155 #, c-format msgid "opendir on \"%s\" failed: %s" msgstr "打开文件夹\"%s\"失败,%s" #: src/main/iptux.cpp:151 #, c-format msgid "option parsing failed: %s\n" msgstr "选项解析失败: %s\n" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "路径 %s 不是文件或者目录: st_mode(%x)" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "接收" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "常规文件" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "发送" #: src/iptux/AnalogFS.cpp:141 #, c-format msgid "stat file \"%s\" failed: %s" msgstr "查看文件\"%s\"状态失败,%s" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "未知" iptux-0.7.4/po/zh_TW.po000066400000000000000000000674121323207530100147120ustar00rootroot00000000000000# Chinese (traditional) translation for iptux # Copyright (C) 2009 THE IPTUX'S COPYRIGHT HOLDER # This file is distributed under the same license as the iptux package. # 村仔 , 2009. # msgid "" msgstr "" "Project-Id-Version: iptux 0.6.3\n" "Report-Msgid-Bugs-To: https://github.com/iptux-src/iptux/issues/new\n" "POT-Creation-Date: 2018-01-24 19:51+0800\n" "PO-Revision-Date: 2010-03-26 00:21+0800\n" "Last-Translator: zhangjiejing \n" "Language-Team: Chinese (traditional) \n" "Language: zh_TW\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "X-Generator: Lokalize 0.3\n" "Plural-Forms: nplurals=2; plural=n != 1;\n" #: src/iptux/dialog.cpp:139 src/iptux/dialog.cpp:200 msgid "" "\n" "Empty Password!" msgstr "" "\n" "密碼為空!" #: src/iptux/DetectPal.cpp:117 src/iptux/DataSettings.cpp:1440 #: src/iptux/DataSettings.cpp:1447 #, c-format msgid "" "\n" "Illegal IP(v4) address: %s!" msgstr "" "\n" "非法的IP(v4)位址:%s!" #: src/iptux/dialog.cpp:195 msgid "" "\n" "Password Mismatched!" msgstr "" "\n" "密碼不一致!" #: src/iptux/DialogPeer.cpp:431 msgid "" "\n" "Photo:\n" msgstr "" "\n" "個人頭象:\n" #: src/iptux/DialogPeer.cpp:1043 src/iptux/DialogPeer.cpp:1114 #, c-format msgid "%s Of %s Received." msgstr "" #: src/iptux/DialogBase.cpp:869 #, c-format msgid "%s Of %s Sent." msgstr "" #: src/iptux/DialogBase.cpp:226 #, c-format msgid "%s To Send." msgstr "" #: src/iptux/DialogPeer.cpp:1039 src/iptux/DialogPeer.cpp:1110 #, c-format msgid "%s to Receive." msgstr "" #: src/iptux/dialog.cpp:121 #, c-format msgid "(%s)[%s]Password:" msgstr "(%s)[%s]密碼: " #: src/main/iptux.cpp:147 msgid "- A software for sharing in LAN" msgstr "" #: src/iptux/HelpDialog.cpp:92 src/iptux/HelpDialog.cpp:111 msgid "..." msgstr "..." #: src/iptux/CoreThread.cpp:922 msgid "" msgstr "<錯誤>" #: src/iptux/HelpDialog.cpp:75 msgid "A GTK+ based LAN Messenger." msgstr "基於GTK+的區域網路通信工具" #: src/iptux/DialogPeer.cpp:787 msgid "Accept" msgstr "接受" #: src/iptux/dialog.cpp:101 msgid "Access Password" msgstr "存取密碼" #: src/iptux/DataSettings.cpp:360 msgid "Activate the sound support" msgstr "啟動聲音支援" #: src/iptux/DataSettings.cpp:455 msgid "Add" msgstr "新增" #: src/iptux/ShareFile.cpp:140 msgid "Add Files" msgstr "新增檔案" #: src/iptux/ShareFile.cpp:143 msgid "Add Folders" msgstr "新增目錄" #: src/iptux/DataSettings.cpp:467 msgid "Added IP(v4) Section:" msgstr "已添加的IP(v4)網路區段:" #: src/iptux/DialogPeer.cpp:411 src/iptux/MainWindow.cpp:1589 #, c-format msgid "Address: %s\n" msgstr "位址: %s\n" #: src/iptux/DialogPeer.cpp:409 src/iptux/MainWindow.cpp:1587 #, c-format msgid "Address: %s(%s)\n" msgstr "位址: %s(%s)\n" #: src/iptux/dialog.cpp:56 msgid "Agree" msgstr "允許" #: src/iptux/ShareFile.cpp:98 msgid "Apply" msgstr "套用" #: src/iptux/MainWindow.cpp:852 src/iptux/DialogGroup.cpp:457 msgid "Ascending" msgstr "升冪" #: src/iptux/DialogPeer.cpp:321 src/iptux/DialogBase.cpp:344 msgid "Attach File" msgstr "新增檔案" #: src/iptux/DialogPeer.cpp:328 src/iptux/DialogBase.cpp:351 msgid "Attach Folder" msgstr "新增目錄" #: src/iptux/DataSettings.cpp:325 msgid "Automatically clean up the chat history" msgstr "自動清空聊天記錄" #: src/iptux/DataSettings.cpp:310 msgid "Automatically hide the panel after login" msgstr "程序啟動後隱藏面板" #: src/iptux/DataSettings.cpp:315 msgid "Automatically open the File Transmission Management" msgstr "自動打開檔案傳輸管理器" #: src/iptux/DataSettings.cpp:305 msgid "Automatically open the chat dialog" msgstr "自動打開聊天對話框" #: src/iptux/RevisePal.cpp:153 msgid "Be SURE to know what you are doing!" msgstr "你最好明白你到底在做些什麼!" #: src/iptux/RevisePal.cpp:173 msgid "Be compatible with iptux's protocol (DANGEROUS)" msgstr "相容 iptux 擴展協議(危險)" #: src/iptux/DataSettings.cpp:437 msgid "Beginning of the IP(v4) section" msgstr "IP(v4)網路區段起始點" #: src/iptux/CoreThread.cpp:1090 msgid "Broadcast" msgstr "廣播" #: src/iptux/MainWindow.cpp:841 src/iptux/DialogGroup.cpp:446 msgid "By IP" msgstr "依 IP" #: src/iptux/MainWindow.cpp:833 src/iptux/DialogGroup.cpp:438 msgid "By Nickname" msgstr "依暱稱" #: src/iptux/support.cpp:97 msgid "Can't find any available web browser!\n" msgstr "未發現可用的瀏覽器!\n" #: src/iptux/DetectPal.cpp:69 src/iptux/ShareFile.cpp:99 msgid "Cancel" msgstr "取消" #: src/iptux/DataSettings.cpp:267 msgid "Candidate network coding" msgstr "預設網路編碼" #: src/iptux/DataSettings.cpp:261 msgid "Candidate network coding:" msgstr "預設網路編碼:" #: src/iptux/MainWindow.cpp:1529 msgid "Change Info." msgstr "更改資訊" #: src/iptux/RevisePal.cpp:97 msgid "Change Pal's Information" msgstr "更改好友資訊" #: src/iptux/DialogBase.cpp:301 msgid "Chat History" msgstr "聊天記錄" #: src/iptux/DialogBase.cpp:414 msgid "Choose enclosure files" msgstr "選擇檔案附件" #: src/iptux/DialogBase.cpp:417 msgid "Choose enclosure folders" msgstr "選擇目錄附件" #: src/iptux/ShareFile.cpp:401 msgid "Choose the files to share" msgstr "選擇共享檔案" #: src/iptux/ShareFile.cpp:404 msgid "Choose the folders to share" msgstr "選擇共享目錄" #: src/iptux/DataSettings.cpp:494 msgid "Clear" msgstr "清空" #: src/iptux/DialogPeer.cpp:372 src/iptux/DialogGroup.cpp:425 msgid "Clear Buffer" msgstr "清空暫存" #: src/iptux/ShareFile.cpp:149 msgid "Clear Password" msgstr "清除密碼" #: src/iptux/MainWindow.cpp:1473 msgid "Clear Tasklist" msgstr "清理任務" #: src/iptux/DataSettings.cpp:1191 src/iptux/DialogGroup.cpp:575 msgid "Clear Up" msgstr "清空" #: src/iptux/DialogPeer.cpp:345 src/iptux/DialogBase.cpp:278 #: src/iptux/DialogBase.cpp:370 msgid "Close" msgstr "關閉" #: src/iptux/DialogPeer.cpp:417 src/iptux/MainWindow.cpp:1595 msgid "Compatibility: GNU/Linux\n" msgstr "相容性: GNU/Linux\n" #: src/iptux/DialogPeer.cpp:415 src/iptux/MainWindow.cpp:1593 msgid "Compatibility: Microsoft\n" msgstr "相容性: Microsoft\n" #: src/iptux/MainWindow.cpp:1156 msgid "Completed" msgstr "已完成" #: src/iptux/dialog.cpp:35 msgid "Confirm Exit" msgstr "確認退出" #: src/iptux/HelpDialog.cpp:92 msgid "Contributors" msgstr "貢獻者" #: src/iptux/MainWindow.cpp:1168 msgid "Cost" msgstr "花費時間" #: src/iptux/DataSettings.cpp:460 msgid "Delete" msgstr "刪除" #: src/iptux/MainWindow.cpp:1544 msgid "Delete Pal" msgstr "刪除好友" #: src/iptux/ShareFile.cpp:146 msgid "Delete Resources" msgstr "刪除資源" #: src/iptux/MainWindow.cpp:860 src/iptux/DialogGroup.cpp:465 msgid "Descending" msgstr "降冪" #: src/iptux/DataSettings.cpp:819 msgid "Description" msgstr "描述" #: src/iptux/DialogPeer.cpp:797 src/iptux/DialogBase.cpp:733 msgid "Detail" msgstr "" #: src/iptux/DetectPal.cpp:69 msgid "Detect" msgstr "搜尋" #: src/iptux/DetectPal.cpp:68 msgid "Detect pals" msgstr "搜尋好友" #: src/iptux/DialogBase.cpp:727 msgid "Dirs" msgstr "" #: src/iptux/DialogPeer.cpp:735 #, fuzzy msgid "Enclosure." msgstr "附件" #: src/iptux/DataSettings.cpp:447 msgid "End of the IP(v4) section" msgstr "IP(v4)網路區段終止點" #: src/iptux/dialog.cpp:162 msgid "Enter a New Password" msgstr "輸入一個新的密碼" #: src/iptux/output.cpp:85 msgid "Error" msgstr "錯誤" #: src/iptux/DataSettings.cpp:772 msgid "Event" msgstr "事件" #: src/iptux/DataSettings.cpp:490 msgid "Export" msgstr "匯出" #: src/iptux/SoundSystem.cpp:145 #, c-format msgid "Failed to play the prompt tone, %s\n" msgstr "播放提示音失敗,%s\n" #: src/iptux/RecvFileData.cpp:312 #, c-format msgid "Failed to receive the directory \"%s\" from %s!" msgstr "接收目錄\"%s\"來自%s失敗!" #: src/iptux/RecvFileData.cpp:171 #, c-format msgid "Failed to receive the file \"%s\" from %s!" msgstr "接收檔案\"%s\"來自%s失敗!" #: src/iptux/SendFileData.cpp:274 #, c-format msgid "Failed to send the directory \"%s\" to %s!" msgstr "傳送目錄\"%s\"到%s失敗!" #: src/iptux/SendFileData.cpp:150 #, c-format msgid "Failed to send the file \"%s\" to %s!" msgstr "傳送檔案\"%s\"到%s失敗!" #: src/iptux/support.cpp:131 #, fuzzy, c-format msgid "" "Fatal Error!!\n" "Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "致命錯誤!!\n" "連接TCP/UDP端口(2425)失敗!\n" "%s" #: src/iptux/support.cpp:115 src/iptux/RecvFileData.cpp:139 #: src/iptux/RecvFileData.cpp:198 src/iptux/DialogPeer.cpp:708 #: src/iptux/CoreThread.cpp:228 #, c-format msgid "" "Fatal Error!!\n" "Failed to create new socket!\n" "%s" msgstr "" "致命錯誤!!\n" "建立新的連接失敗!\n" "%s" #: src/iptux/support.cpp:128 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n" "%s" msgstr "" "致命錯誤!!\n" "連接TCP/UDP端口(2425)失敗!\n" "%s" #: src/iptux/support.cpp:113 #, fuzzy, c-format msgid "" "Fatal Error!! Failed to create new socket!\n" "%s" msgstr "" "致命錯誤!!\n" "建立新的連接失敗!\n" "%s" #: src/iptux/ShareFile.cpp:256 msgid "File" msgstr "檔案" #: src/iptux/DialogPeer.cpp:826 #, fuzzy msgid "File received." msgstr "收到訊息" #: src/iptux/DialogPeer.cpp:780 msgid "File to be receive." msgstr "" #: src/iptux/DialogBase.cpp:719 msgid "File to send." msgstr "" #: src/iptux/dialog.cpp:32 msgid "" "File transfer has not been completed.\n" "Are you sure to cancel and quit?" msgstr "" "檔案傳輸尚未完成。\n" "你確定要取消任務並退出嗎?" #: src/iptux/MainWindow.cpp:1144 msgid "Filename" msgstr "檔案名" #: src/iptux/DialogBase.cpp:730 #, fuzzy msgid "Files" msgstr "檔案" #: src/iptux/MainWindow.cpp:539 msgid "Files Transmission Management" msgstr "檔案傳輸管理器" #: src/iptux/DataSettings.cpp:339 msgid "Filter the request of sharing files" msgstr "過濾共享檔案請求" #: src/iptux/DataSettings.cpp:1103 src/iptux/DataSettings.cpp:1134 #, c-format msgid "" "Fopen() file \"%s\" failed!\n" "%s" msgstr "" "打開檔案\"%s\"失敗!\n" "%s" #: src/iptux/DataSettings.cpp:805 msgid "From" msgstr "起始" #: src/iptux/DataSettings.cpp:431 msgid "From:" msgstr "起始:" #: src/iptux/MainWindow.cpp:1068 msgid "Group" msgstr "群組名稱" #: src/iptux/HelpDialog.cpp:92 msgid "Help" msgstr "幫助" #: src/iptux/MainWindow.cpp:1086 msgid "Host" msgstr "主機" #: src/iptux/DialogPeer.cpp:404 src/iptux/MainWindow.cpp:1582 #, c-format msgid "Host: %s\n" msgstr "主機: %s\n" #: src/iptux/MainWindow.cpp:1074 src/iptux/MainWindow.cpp:1138 msgid "IPv4" msgstr "IPv4" #: src/iptux/DataSettings.cpp:486 msgid "Import" msgstr "匯入" #: src/iptux/DialogPeer.cpp:284 msgid "Info." msgstr "資訊" #: src/iptux/output.cpp:40 msgid "Information" msgstr "資訊" #: src/iptux/DialogPeer.cpp:367 msgid "Insert Picture" msgstr "插入圖片" #: src/iptux/HelpDialog.cpp:101 msgid "" "It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n" "\n" "Especially, Here's some we would like to thank much:\n" "\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..." msgstr "" #: src/iptux/HelpDialog.cpp:59 src/iptux/HelpDialog.cpp:61 msgid "Jally " msgstr "" #: src/iptux/HelpDialog.cpp:62 msgid "LiWeijian " msgstr "牛牛 " #: src/iptux/support.cpp:52 msgid "Loading the process successfully!" msgstr "程序載入成功!" #: src/iptux/HelpDialog.cpp:60 src/iptux/HelpDialog.cpp:63 msgid "ManPT " msgstr "" #: src/iptux/DialogGroup.cpp:299 msgid "Member" msgstr "成員" #: src/iptux/DataSettings.cpp:705 msgid "Message received" msgstr "收到訊息" #: src/iptux/DialogPeer.cpp:1050 src/iptux/DialogBase.cpp:875 #, fuzzy msgid "Mission Completed!" msgstr "已完成" #: src/iptux/AnalogFS.cpp:125 #, c-format msgid "Mkdir() directory \"%s\" failed, %s" msgstr "建立目錄\"%s\"失敗,%s" #: src/iptux/HelpDialog.cpp:118 msgid "More About Iptux" msgstr "更多..." #: src/iptux/DialogPeer.cpp:932 src/iptux/DialogBase.cpp:787 msgid "Name" msgstr "" #: src/iptux/DataSettings.cpp:65 msgid "Network" msgstr "網路" #: src/iptux/MainWindow.cpp:1057 msgid "Nickname" msgstr "暱稱" #: src/iptux/DialogPeer.cpp:398 src/iptux/MainWindow.cpp:1576 #, c-format msgid "Nickname: %s\n" msgstr "暱稱: %s\n" #: src/iptux/DialogPeer.cpp:396 src/iptux/MainWindow.cpp:1574 #, c-format msgid "Nickname: %s@%s\n" msgstr "暱稱: %s@%s\n" #: src/iptux/ShareFile.cpp:98 msgid "OK" msgstr "確定" #: src/iptux/MainWindow.cpp:1457 msgid "Open Containing Folder" msgstr "打開所在的文件夾" #: src/iptux/MainWindow.cpp:1451 msgid "Open This File" msgstr "打開此文件" #: src/iptux/AnalogFS.cpp:83 src/iptux/AnalogFS.cpp:87 #, c-format msgid "Open() file \"%s\" failed, %s" msgstr "打開檔案\"%s\"失敗,%s" #: src/iptux/AnalogFS.cpp:198 #, c-format msgid "Opendir() directory \"%s\" failed, %s" msgstr "打開目錄\"%s\"失敗,%s" #: src/iptux/CoreThread.cpp:526 src/iptux/CoreThread.cpp:549 #: src/iptux/CoreThread.cpp:1042 src/iptux/CoreThread.cpp:1067 msgid "Others" msgstr "其他" #: src/iptux/DataSettings.cpp:284 msgid "Pal's default face picture:" msgstr "預設好友頭像:" #: src/iptux/RevisePal.cpp:159 msgid "Pal's face picture:" msgstr "好友頭像:" #: src/iptux/RevisePal.cpp:135 msgid "Pal's group name:" msgstr "好友群組名稱:" #: src/iptux/RevisePal.cpp:123 msgid "Pal's nickname:" msgstr "好友暱稱:" #: src/iptux/DialogGroup.cpp:397 msgid "Pals" msgstr "好友" #: src/iptux/MainWindow.cpp:1630 #, c-format msgid "Pals Online: %" msgstr "線上好友: %" #: src/iptux/MainWindow.cpp:650 msgid "Pals Online: 0" msgstr "線上好友: 0" #: src/iptux/DataSettings.cpp:297 msgid "Panel font:" msgstr "面板字體:" #: src/iptux/dialog.cpp:171 msgid "Password: " msgstr "密碼: " #: src/iptux/DialogBase.cpp:799 msgid "Path" msgstr "" #: src/iptux/DialogBase.cpp:780 msgid "PeelName" msgstr "" #: src/iptux/MainWindow.cpp:1132 msgid "Peer" msgstr "好友" #: src/iptux/DataSettings.cpp:57 msgid "Personal" msgstr "個人" #: src/iptux/DataSettings.cpp:219 msgid "Photo" msgstr "個人相片" #: src/iptux/DataSettings.cpp:764 msgid "Play" msgstr "播放" #: src/iptux/DetectPal.cpp:94 msgid "Please input an IP address (IPv4 only)!" msgstr "請輸入IP位址(限IPv4格式)!" #: src/iptux/DetectPal.cpp:86 msgid "Please input an IP address (IPv4 only):" msgstr "請輸入IP位址(限IPv4格式):" #: src/iptux/RevisePal.cpp:141 msgid "Please input pal's new group name!" msgstr "請輸入好友的新群組名稱!" #: src/iptux/RevisePal.cpp:129 msgid "Please input pal's new nickname!" msgstr "請輸入好友的新暱稱!" #: src/iptux/dialog.cpp:107 msgid "Please input the password for the shared files behind" msgstr "請輸入共享檔案的存取密碼" #: src/iptux/DataSettings.cpp:191 msgid "Please input your group name!" msgstr "請輸入您的群組名稱!" #: src/iptux/DataSettings.cpp:180 msgid "Please input your nickname!" msgstr "請輸入您的暱稱!" #: src/iptux/RevisePal.cpp:413 src/iptux/DataSettings.cpp:1281 msgid "Please select a face picture" msgstr "請選擇一個頭像圖片" #: src/iptux/DataSettings.cpp:1540 msgid "Please select a file to import data" msgstr "請選擇匯入資料的檔案" #: src/iptux/dialog.cpp:226 #, fuzzy msgid "Please select a folder to save files." msgstr "請選擇一個聲音檔案" #: src/iptux/DataSettings.cpp:1303 msgid "Please select a personal photo" msgstr "請選擇個人照片" #: src/iptux/DialogPeer.cpp:669 msgid "Please select a picture to insert the buffer" msgstr "請選擇插入緩衝區的圖片" #: src/iptux/DataSettings.cpp:869 msgid "Please select a sound file" msgstr "請選擇一個聲音檔案" #: src/iptux/DataSettings.cpp:835 msgid "Please select download folder" msgstr "請選擇下載目錄" #: src/iptux/DataSettings.cpp:278 msgid "" "Preference network coding (You should be aware of what you are doing if you " "want to modify it.)" msgstr "偏好網路編碼(如果你想要修改它,那麼你必須明白你正在做什麼。)" #: src/iptux/DataSettings.cpp:272 msgid "Preference network coding:" msgstr "偏好網路編碼:" #: src/iptux/DataSettings.cpp:148 msgid "Preferences" msgstr "偏好設定" #: src/iptux/MainWindow.cpp:1163 msgid "Progress" msgstr "進度" #: src/iptux/HelpDialog.cpp:94 #, fuzzy msgid "" "Project Home: \n" "https://github.com/iptux-src/iptux\n" "\n" "User and Developer Group: \n" "https://groups.google.com/group/iptux/\n" "\n" "Note that you can get help form the project wiki page.\n" "\n" "If you find no solutions in any of the existed documents, feel free to drop " "a email at iptux@googlegroups.com, lots of users and developers would be " "glade to help about your problems." msgstr "" "程式發展首頁: \n" "http://code.google.com/p/iptux/\n" "\n" "郵件討論群組: \n" "https://groups.google.com/group/iptux/\n" "\n" "遇到問題時,麻煩留意一下項目Wiki頁面,會得到不少幫助的資訊。\n" "\n" "如果仍然找不到解決的辦法,歡迎發信到郵件群組iptux@googlegroups.com,我們會樂" "意幫助你解決問題。" #: src/iptux/MainWindow.cpp:1180 msgid "Rate" msgstr "速率" #: src/iptux/RecvFileData.cpp:315 #, c-format msgid "Receive the directory \"%s\" from %s successfully!" msgstr "接收目錄\"%s\"來自%s成功!" #: src/iptux/RecvFileData.cpp:174 #, c-format msgid "Receive the file \"%s\" from %s successfully!" msgstr "接收檔案\"%s\"來自%s成功!" #: src/iptux/DialogPeer.cpp:1036 src/iptux/DialogPeer.cpp:1107 msgid "Receiving Progress." msgstr "" #: src/iptux/DialogPeer.cpp:784 msgid "Receiving progress." msgstr "" #: src/iptux/LogSystem.cpp:55 #, c-format msgid "Recevied-From: Nickname:%s User:%s Host:%s" msgstr "来自: 昵称:%s 用户:%s 主機:%s" #: src/iptux/DialogPeer.cpp:792 src/iptux/dialog.cpp:56 msgid "Refuse" msgstr "拒絕" #: src/iptux/MainWindow.cpp:1174 msgid "Remaining" msgstr "剩餘時間" #: src/iptux/DialogPeer.cpp:1254 src/iptux/DialogBase.cpp:360 #: src/iptux/DialogBase.cpp:663 #, fuzzy msgid "Remove Selected" msgstr "反選" #: src/iptux/dialog.cpp:180 msgid "Repeat: " msgstr "重複: " #: src/iptux/DialogPeer.cpp:335 src/iptux/dialog.cpp:55 #: src/iptux/MainWindow.cpp:1515 msgid "Request Shared Resources" msgstr "請求共享資源" #: src/iptux/DataSettings.cpp:1186 src/iptux/DialogGroup.cpp:570 msgid "Reverse Select" msgstr "反選" #: src/iptux/DataSettings.cpp:1587 msgid "Save data to file" msgstr "保存資料到檔案" #: src/iptux/DataSettings.cpp:209 msgid "Save files to: " msgstr "檔案存至:" #: src/iptux/DataSettings.cpp:329 msgid "Save the chat history" msgstr "儲存聊天記錄" #: src/iptux/DialogPeer.cpp:875 msgid "SaveAs" msgstr "" #: src/iptux/MainWindow.cpp:731 msgid "Search Pals" msgstr "搜尋好友" #: src/iptux/DataSettings.cpp:1181 src/iptux/DialogGroup.cpp:565 msgid "Select All" msgstr "全選" #: src/iptux/DataSettings.cpp:857 msgid "Select Font" msgstr "選擇字體" #: src/iptux/DialogBase.cpp:282 src/iptux/DialogGroup.cpp:390 msgid "Send" msgstr "傳送" #: src/iptux/MainWindow.cpp:1493 msgid "Send Message" msgstr "傳送訊息" #: src/iptux/SendFileData.cpp:277 #, c-format msgid "Send the directory \"%s\" to %s successfully!" msgstr "傳送目錄\"%s\"到%s失敗!" #: src/iptux/SendFileData.cpp:153 #, c-format msgid "Send the file \"%s\" to %s successfully!" msgstr "傳送檔案\"%s\"到%s成功!" #: src/iptux/LogSystem.cpp:62 msgid "Send-Broadcast" msgstr "傳送廣播" #: src/iptux/LogSystem.cpp:59 #, c-format msgid "Send-To: Nickname:%s User:%s Host:%s" msgstr "傳送: 暱稱:%s 用戶:%s 主機:%s" #: src/iptux/DialogBase.cpp:866 #, fuzzy msgid "Sending Progress." msgstr "進度" #: src/iptux/DialogBase.cpp:724 msgid "Sending progress." msgstr "" #: src/iptux/ShareFile.cpp:153 msgid "Set Password" msgstr "設置密碼" #: src/iptux/ShareFile.cpp:97 msgid "Shared Files Management" msgstr "共享檔案管理器" #: src/iptux/DataSettings.cpp:231 msgid "Signature" msgstr "個人簽名" #: src/iptux/DialogPeer.cpp:424 src/iptux/MainWindow.cpp:1602 msgid "Signature:\n" msgstr "個性簽名:\n" #: src/iptux/DialogPeer.cpp:881 src/iptux/DialogPeer.cpp:938 #: src/iptux/ShareFile.cpp:266 src/iptux/DialogBase.cpp:793 #: src/iptux/MainWindow.cpp:1150 msgid "Size" msgstr "大小" #: src/iptux/DialogGroup.cpp:432 msgid "Sort" msgstr "排序" #: src/iptux/DataSettings.cpp:62 msgid "Sound" msgstr "聲音" #: src/iptux/DataSettings.cpp:376 msgid "Sound Event" msgstr "聲音事件" #: src/iptux/DialogPeer.cpp:868 src/iptux/DialogPeer.cpp:926 msgid "Source" msgstr "來源" #: src/iptux/AnalogFS.cpp:105 #, c-format msgid "Stat64() file \"%s\" failed, %s" msgstr "獲取檔案\"%s\"狀態失敗,%s" #: src/iptux/MainWindow.cpp:1120 msgid "State" msgstr "狀態" #: src/iptux/DataSettings.cpp:409 msgid "Stop" msgstr "停止" #: src/iptux/DataSettings.cpp:59 msgid "System" msgstr "系統" #: src/iptux/RevisePal.cpp:147 msgid "System coding:" msgstr "系統編碼:" #: src/iptux/DialogPeer.cpp:420 src/iptux/MainWindow.cpp:1598 #, c-format msgid "System coding: %s\n" msgstr "系統編碼: %s\n" #: src/iptux/DialogPeer.cpp:189 #, fuzzy, c-format msgid "Talk with %s(%s) IP:%s" msgstr "與%s對話" #: src/iptux/DialogGroup.cpp:207 #, c-format msgid "Talk with the group %s" msgstr "與%s組對話" #: src/iptux/MainWindow.cpp:1126 msgid "Task" msgstr "任務" #: src/iptux/MainWindow.cpp:1468 msgid "Terminate All" msgstr "終止所有" #: src/iptux/MainWindow.cpp:1463 msgid "Terminate Task" msgstr "終止任務" #: src/iptux/DataSettings.cpp:406 msgid "Test" msgstr "測試" #: src/iptux/MainWindow.cpp:1850 msgid "The file you want to open not exist!" msgstr "" #: src/iptux/DetectPal.cpp:122 #, c-format msgid "The notification has been sent to %s." msgstr "訊息已經傳送到%s。" #: src/iptux/MainWindow.cpp:1878 msgid "The path you want to open not exist!" msgstr "" #: src/iptux/support.cpp:68 msgid "The process is about to quit!" msgstr "程序即將退出!" #: src/iptux/DataSettings.cpp:812 msgid "To" msgstr "終止" #: src/iptux/StatusIcon.cpp:224 #, c-format msgid "To be read: %u messages" msgstr "未讀訊息: %u條" #: src/iptux/DataSettings.cpp:441 msgid "To:" msgstr "終止:" #: src/iptux/DataSettings.cpp:701 msgid "Transfer finished" msgstr "傳輸完成" #: src/iptux/ShareFile.cpp:272 msgid "Type" msgstr "類型" #: src/iptux/DataSettings.cpp:320 msgid "Use the 'Enter' key to send message" msgstr "使用Enter鍵傳送訊息" #: src/iptux/DataSettings.cpp:334 msgid "Use the Blacklist (NOT recommended)" msgstr "開啟黑名單處理方案(不推薦)" #: src/iptux/MainWindow.cpp:1080 msgid "User" msgstr "用戶" #: src/iptux/DialogPeer.cpp:401 src/iptux/MainWindow.cpp:1579 #, c-format msgid "User: %s\n" msgstr "用戶: %s\n" #: src/iptux/LogSystem.cpp:84 #, c-format msgid "User:%s Host:%s" msgstr "用戶:%s 主機:%s" #: src/iptux/DialogPeer.cpp:392 src/iptux/MainWindow.cpp:1570 #, c-format msgid "Version: %s\n" msgstr "版本: %s\n" #: src/iptux/DataSettings.cpp:367 msgid "Volume Control: " msgstr "音量控制:" #: src/iptux/output.cpp:63 msgid "Warning" msgstr "警告" #: src/iptux/DataSettings.cpp:196 msgid "Your face picture:" msgstr "您的頭像:" #: src/iptux/DataSettings.cpp:185 msgid "Your group name:" msgstr "您的群組名稱:" #: src/iptux/DataSettings.cpp:174 msgid "Your nickname:" msgstr "您的暱稱:" #: src/iptux/dialog.cpp:72 #, c-format msgid "" "Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?" msgstr "" "您的好友(%s)[%s]\n" "請求獲取您的共享資源,\n" "是否允許?" #: src/iptux/Command.cpp:221 msgid "Your pal didn't receive the packet. He or she is offline maybe." msgstr "你的好友沒有收到傳送的資料,他可能已經下線。" #: src/iptux/StatusIcon.cpp:135 src/iptux/MainWindow.cpp:754 msgid "_Detect" msgstr "搜尋(_D)" #: src/iptux/MainWindow.cpp:904 msgid "_FAQ" msgstr "FAQ(_F)" #: src/iptux/DialogPeer.cpp:317 src/iptux/DialogBase.cpp:340 #: src/iptux/MainWindow.cpp:749 msgid "_File" msgstr "檔案(_F)" #: src/iptux/MainWindow.cpp:763 msgid "_Find" msgstr "尋找(_F)" #: src/iptux/DialogBase.cpp:389 src/iptux/MainWindow.cpp:890 msgid "_Help" msgstr "幫助(_H)" #: src/iptux/StatusIcon.cpp:92 msgid "_Hide" msgstr "隱藏(_H)" #: src/iptux/MainWindow.cpp:899 msgid "_More" msgstr "更多(_M)" #: src/iptux/StatusIcon.cpp:114 src/iptux/MainWindow.cpp:800 msgid "_Preferences" msgstr "偏好設定(_P)" #: src/iptux/StatusIcon.cpp:144 src/iptux/MainWindow.cpp:775 msgid "_Quit" msgstr "退出(_Q)" #: src/iptux/StatusIcon.cpp:123 src/iptux/MainWindow.cpp:818 msgid "_Shared Management" msgstr "共享管理器(_S)" #: src/iptux/StatusIcon.cpp:94 msgid "_Show" msgstr "顯示(_S)" #: src/iptux/MainWindow.cpp:827 msgid "_Sort" msgstr "排序(_S)" #: src/iptux/DialogPeer.cpp:363 src/iptux/MainWindow.cpp:794 #: src/iptux/DialogGroup.cpp:419 msgid "_Tools" msgstr "工具(_T)" #: src/iptux/StatusIcon.cpp:105 src/iptux/MainWindow.cpp:809 msgid "_Transmission" msgstr "傳輸管理器(_T)" #: src/iptux/MainWindow.cpp:869 msgid "_Update" msgstr "更新(_U)" #: src/iptux/HelpDialog.cpp:65 msgid "" "alick \n" "ManPT " msgstr "" "alick \n" "ManPT \n" "村仔 " #: src/iptux/ShareFile.cpp:213 src/iptux/ShareFile.cpp:365 msgid "directory" msgstr "目錄" #: src/iptux/MainWindow.cpp:886 #, fuzzy msgid "http://code.google.com/p/iptux/wiki/FAQ?wl=en" msgstr "http://code.google.com/p/iptux/wiki/FAQ" #: src/iptux/StatusIcon.cpp:227 src/iptux/HelpDialog.cpp:70 #: src/iptux/MainWindow.cpp:515 msgid "iptux" msgstr "信使(iptux)" #: src/iptux/MainWindow.cpp:1851 #, fuzzy msgid "iptux Error" msgstr "錯誤" #: src/iptux/UdpData.cpp:133 src/iptux/UdpData.cpp:134 #: src/iptux/UdpData.cpp:566 src/iptux/UdpData.cpp:602 msgid "mysterious" msgstr "神秘訪客" #: src/iptux/AnalogFS.cpp:155 #, fuzzy, c-format msgid "opendir on \"%s\" failed: %s" msgstr "打開目錄\"%s\"失敗,%s" #: src/main/iptux.cpp:151 #, fuzzy, c-format msgid "option parsing failed: %s\n" msgstr "打開目錄\"%s\"失敗,%s" #: src/iptux/AnalogFS.cpp:148 #, c-format msgid "path %s is not file or directory: st_mode(%x)" msgstr "" #: src/iptux/RecvFileData.cpp:106 msgid "receive" msgstr "接收" #: src/iptux/ShareFile.cpp:209 src/iptux/ShareFile.cpp:361 msgid "regular" msgstr "常規檔案" #: src/iptux/SendFileData.cpp:107 msgid "send" msgstr "傳送" #: src/iptux/AnalogFS.cpp:141 #, fuzzy, c-format msgid "stat file \"%s\" failed: %s" msgstr "查看檔案\"%s\"狀態失敗,%s\n" #: src/iptux/RecvFileData.cpp:121 src/iptux/RecvFileData.cpp:249 #: src/iptux/SendFileData.cpp:123 src/iptux/SendFileData.cpp:206 #: src/iptux/CoreThread.cpp:908 src/iptux/ShareFile.cpp:217 #: src/iptux/ShareFile.cpp:369 msgid "unknown" msgstr "未知" #~ msgid "" #~ "\n" #~ "Can't send an empty message!!" #~ msgstr "" #~ "\n" #~ "傳送內容不能為空!!" #~ msgid "Files Receive Management" #~ msgstr "檔案接收管理器" #~ msgid "Free:%s Total:%s" #~ msgstr "空閒:%s 總計:%s" #~ msgid "Opendir() directory \"%s\" failed, %s\n" #~ msgstr "打開目錄\"%s\"失敗,%s\n" #~ msgid "Pal's Shared Resources" #~ msgstr "好友共享的資源" #~ msgid "Recv" #~ msgstr "接收" #~ msgid "Rmdir() directory \"%s\" failed, %s\n" #~ msgstr "刪除目錄\"%s\"失敗,%s\n" #~ msgid "Stat() file \"%s\" failed, %s\n" #~ msgstr "查看檔案\"%s\"狀態失敗,%s\n" #~ msgid "The user is not privileged!\n" #~ msgstr "用戶沒有權限!\n" #~ msgid "Unlink() file \"%s\" failed, %s\n" #~ msgstr "刪除檔案\"%s\"失敗,%s\n" #~ msgid "utf-16" #~ msgstr "big5,gb18030" #~ msgid "utf-8" #~ msgstr "big5" iptux-0.7.4/protocol000066400000000000000000000064651323207530100144660ustar00rootroot00000000000000一、iptux发送数据编码列表(不全,但很容易推导出其他的): 1、广播 首选编码 2、拨号 首选编码 3、通知在线 好友编码 4、变更信息 好友编码 5、未知拨号 首选编码 6、发送消息 好友编码 7、回应消息 好友编码 …… 好友编码 二、iptux接收数据编码处理(确认,意指已有一方成功建立了好友数据结构) 1、对于iptux尚未确认的好友,发送或接收的编码将一概按照首选编码处理! 2、对于iptux已经确认的好友,将要发送的数据必须一概转换成好友编码后才能发送出去;对于接收到的好友数据,如果好友兼容iptux自身协议,数据直接被使用,否则数据必须被转换为本地编码,方可使用! 三、iptux提高功能协议: 1、iptux期望所接收到的任何好友的第一个数据包或信息更改数据包(IPMSG_BR_ABSENCE)为如下格式: (IPMsg协议标准实现)\0(组名)\0(好友头像名)\0(好友编码) 注:好友头像名为文件名,而不是全路径 如果满足如上条件,则认为兼容iptux,iptux将严格使用好友提供的相关数据;否则不兼容,iptux将使用一些软件默认数据来填充好友的数据结构。 2、自定义命令字实现相关功能如下: /* 命令字 */ #define IPTUX_ASKSHARED 0x000000FFUL 请求获取共享文件 #define IPTUX_SENDICON 0x000000FEUL 发送自定义头像数据 #define IPTUX_SENDSUBLAYER 0x000000FDUL 发送底层数据,必须与选项配合使用 #define IPTUX_SENDSIGN 0x000000FCUL 发送个人签名 #define IPTUX_SENDMSG 0x000000FBUL 发送消息,必须与选项配合使用 /* 命令字选项 */ /* option for IPTUX_SENDSUBLAYER */ #define IPTUX_PHOTOPICOPT 0x00000100UL 个人形象图片选项 #define IPTUX_MSGPICOPT 0x00000200UL 消息图片选项 /* option for IPMSG_SENDMSG */ #define IPTUX_SHAREDOPT 0x80000000UL 共享文件选项 /* option for IPMSG_SENDMSG & IPTUX_ASKSHARED */ #define IPTUX_PASSWDOPT 0x40000000UL 密码选项 /* option for IPTUX_SENDMSG */ #define IPTUX_REGULAROPT 0x00000100UL #define IPTUX_SEGMENTOPT 0x00000200UL #define IPTUX_GROUPOPT 0x00000300UL #define IPTUX_BROADCASTOPT 0x00000400UL 1)当iptux接收到IPTUX_ASKSHARED命令字的数据包时,就应该直接将软件设置的共享文件提供给请求者或是先向使用者(用户)询问; 2)当iptux接收到IPTUX_SENDICON命令字的数据包时,应该提取数据包的图像数据,然后将好友头像转换为此图像;此命令格式如下: (IPMsg协议标准实现)\0(图像数据) 注:图像数据应为存盘文件中的数据,而不是内存数据;另,图像数据不能超过8096字节 iptux期望在接收到此命令数据包之前,此好友必须已经被确认,否则数据将被丢弃;此命令应该紧跟在(IPMSG_BR_ENTRY,IPMSG_ANSENTRY,IPMSG_BR_ABSENCE)命令数据包之后,但是不紧跟在其后也无关要紧,iptux知道怎么正确处理它; 3)IPTUX_SENDSUBLAYER命令字必须配合选项命令字,使用TCP协议发送,命令格式如下: (IPMsg协议标准实现)\0(数据) 4)当iptux接收到IPTUX_SENDSIGN命令字的数据包时,将提取个人签名; 5)当iptux接收到IPTUX_SENDMSG命令字的数据包时,将按照消息选项分派消息最终去向;此命令字主要用于扩展IPMsg的发送消息命令。 iptux-0.7.4/scripts/000077500000000000000000000000001323207530100143565ustar00rootroot00000000000000iptux-0.7.4/scripts/build_in_docker_ubuntu1604.sh000077500000000000000000000003441323207530100217470ustar00rootroot00000000000000#!/bin/sh set -ex cd `dirname $0`/.. apt-get update apt-get install -y libgtk2.0-dev libglib2.0-dev libgstreamer1.0-dev libjsoncpp-dev g++ make cmake mkdir build && cd build && cmake .. && make && ctest --verbose make install iptux-0.7.4/sound/000077500000000000000000000000001323207530100140175ustar00rootroot00000000000000iptux-0.7.4/sound/CMakeLists.txt000066400000000000000000000001361323207530100165570ustar00rootroot00000000000000install(FILES msg.ogg trans.ogg DESTINATION ${CMAKE_INSTALL_DATADIR}/${PROJECT_NAME}/sound )iptux-0.7.4/sound/msg.ogg000066400000000000000000000224731323207530100153130ustar00rootroot00000000000000OggS-F7vorbisD8OggS-vp-vorbisXiph.Org libVorbis I 20070622vorbis"BCV@$s*FsBPBkBL2L[%s!B[(АU@AxA!%=X'=!9xiA!B!B!E9h'A08 8E9X'A B9!$5HP9,(05(0ԃ BI5gAxiA!$AHAFAX9A*9 4d((  @Qqɑɱ  YHHH$Y%Y%Y扪,˲,˲,2 HPQ Eq Yd8Xh爎4CS# G,]6MuC74ӴmUut]_uhPTU]WeUW}[}UUYՖa} Uum]X~2tu[h뺱̾L(CLABH)R9)sRB)RR9&%sNJ(PJKB)RZl՚Z5Z(PJ[k5FAȜ9'Z(9*:)Z,)X9'%J!JL%C*b,)ZlŘs(ŒJl%X[L9s9'%sNJ(RRksR:)eJ*)XJJ1sNJ!BJ%SJRb+)XJjŘsK1PR%KJ1snAh-c(%cC)b,)cŘs(%ƒJ%X[sNZkmsЩZSLsYsZ(PJZ[9Rb+)XJŘskPJ%XKJ5k5ZŘkjs1Sk5kNZsc&BCVQ!J1A141朔1 R1R2 RRR RkRRj4%(4d% `pA'@pBdH4,1$&(@Et.:B H 7<'RpFGHH!DD4OggS@F-<="**+"! !0//'1-*./*%0*+.-#"$#*++&"!"#$*--%&.,.˵ĺ^ T̩Fw<.r"+"2_ leQ2c?{{-Xߝtn ӰsN= B5Amg4Tqed-w=G$쳘ʟGv9&Ű|VYYc׼WdOfgfTVy@,7P+uI<|F5)[-Ndo^7)-Hl0 |DO#"@M-o )M|Dՙ]'vQ_vav<#5g*¡I>Q`8ggSOۙY3w oCLW#_+c! `},.n\rpZY6?֕HD]K@i#)B [Q|Fu«lx8IfPT[lk s9[ *d^ 5E;loۨ'hY \G'0:LkX< LS n rC,EA:tM]?uۂUgNzΤIDWrcQu0`ooY8myyyyyELubT7U6Y7@F*Hѥ? zw#nJh`I!SMsd4Y5|eWx?o9apT˜ \[?v{ߊ^G\]=qu{g>agSNZXT>+ 턠4i\W%wzS>sߕO߯"XԵ_s8_ n ;zj:h8w)! a^(Zq+j:xFe ^gIU跢<,Q֠e(ƞЏ@[~ќyoZHnu!Ь<@V d _?F8v2 ~&@ w88)vaogd9lfu"컜dY$4KTJ+!$(qTMҨs,a8j;XyK.a^ҷ:׭݉I_|5[M YIVy?7V ?^Ih)P {`c\WޯWZ EcCfQ8<|TaGTW!4e#Ax%n[ !\iE_d)xתpd[伺V]F\ ™>4 M-nlȩ.s( vo52+R_!FWvL4]oR供+ @0YI÷f0 ,<:y%1>G#{0@q$8^*}g&nP/Fhv;?dFVم_>zon!ВL"=.v͝!;Z2 0sT`'/5p$a+b09윒(Q=[3A  ؔFP$jVKVlBIJ-<[d ]u߹WUG@3U+񢡊iT[wdђ_Ȥta!I8߮st ·`r In&ˤ{/"b J~  A9!ҽB*-P9ѡwh䎯[$v!b(2i+ Br;pVO2Vأ(@3R/I-I4_q&4"(c53<7빾9;+/6h av5sq<4+im7H2";Y/Xk.Fq5H;~a% .%u6J'ٓA4PW700L.}'Tg狋Md&LfDyq@zNC[2oӈzozevMkD rGk{Q~Z?n/yچbOn0kc75n 5Q &Q.azh!=9ȢdO{T]7xȢtjAse?50f8s(0(2CġmM7")84 /G|N#'s٫f|ڥhp|,`fPCgod#zk1+{M t/(OggSo-K U޷w{oO9#2 yoƛ87㣱Wv֌t IgzÈasUA{&PWO[kޥdn"-L{&gf{u(dd צv͍FQ &2K~"gr܉ןD2$xgoK&!ϝ,lְda$>$=̧k1Ȑ4ğ>EvDx7%aBQmG'9`,w6x66*BP9WA$Ha2%Efcfw*PJrC C=]`%|rnmPN9̊SQV1n4L="622;T"lem^vgϔ=Pr{f'3$K.Z)/m?5dX$=)ol 0*s\q< #P@*v?!SZ9מN"P2aֵ6w#De|#ιW_-1iȀĨ&OO2]e|Pf1~xh{{{w_HxL'Ah,:wݑziAdHM?eSg! 71`̏+D98V@㵂H6#XX2ʑ.WcZ7/&¬sh&!Ye|R:&I>So Lj)q2*X/g9E=b'y7¸e^wL )aW8?`شX%pjLT\b01IlmJ SE߈:i]F}S4ͶP13*M D929M[·  '*vP$t $np`ѻau,q3o.wocՊຢOGw_ 5^NsMw{ݡ$i}G.t@:֊Q췧3a\fuQw[uU5S="EJGUdm:+,/@ZϸkR7zf"cǜ/4%9mېTjfx p4GD}'rVώfeuox/3 Is-Wg#醄a?j f LcPXsyCxzr˜QbwhCf3:.9Xu܏ߞ| >8D-]Ɔڎ}njJR`Ly>8_g.J?+g_~ IHWE#+b-9N?()7zNޕ|zܶd83B3@gPP aMj~cvqNߌ(r\\vY} iptux-0.7.4/sound/trans.ogg000066400000000000000000000071761323207530100156570ustar00rootroot00000000000000OggS`(RtvorbisOggS`(Rv -vorbisXiph.Org libVorbis I 20070622vorbisBCV R!%SJcRR)cP[Gc9F!dSI{O*XJRX)ESLSIR)EcSH!S1esKI %lMtKc1FcZJc1EcRRIs:f%d:Fb|0:B(R-[S-KiasJjc1S(АU@BCV P EQАU@EqqG$BCV@((#IdYeYy/.!I̐SI&)U99dRƘbQΐS 11)N9 "CHd K=b8"A!Ɛs J!rI D9)LJ(I -"眔NJ&RˤB+8XRH)ĔbN1R)ǐR9Řr1 T1H)sN9 d * 2B!+8$iihi(z(y陦zlyiz)k늪j˦ڶ骶ʲn۞ʶnml,ۺyꙦz麪ڲ꺲홦늪+ۦʲʶʲk麢ڮʮmʺʲ۶ 躶ʮ-lBT3MLuU׵mum[3M5]WEueՕu]ue[LuMWeUeYeveWE׵mU}]ue_meY}uu[eWeYe]Y}SU[7]WM}[}am]WUօUu}eu0,뾮00m ëƱ뾮ܾj۾1nƱm+loq,ʾo/ *˺ڲ˺. jںp̲. +ǯ Cնuo 7v@!+8!c* R !T1!cJJI!* dIJhJ(PJKRj-Z JiZj)Rlc2dI(VJi)sLJƠB*JIeIɠ9HRIPJkJJJmJi-ZIRmZ# dAɜRJIZ朔:*J)RA(%JIJ+JJRZk՘RK5ZIPJkS+5PR JiVkj-PBkK*1cmJi[)[XSK5blJ-9ZkJ-R[LXk %JiZJZJ*ZlZ5b))JlX[l5blXR1XsKՔZXK+5kn5R@ eА@` cAhr9)R9'%sB)eA!99B))[(%Z, M Y D ( c*sBcAsA)cA'%B)B( lДXА@` b 1 tR:)LJ'Z )eJ%ZH 2k%bFXb*B(4d%@c9gb9!41*ƜsBc9!9 BsBBA!RJ B)tBR *pQdsBCVy1J9'%F) [cRjb BJX1!b ZvRj-ZCJXk!b5Z{j-ZsιE6' *4d%@ c9b1CJ1Ƙs)s9c9s1s9Ƙs9s9砃9sAs9!t9 *pQdsBCV1RJ)RJRJ)R!RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ)RJ) gXI:+ .4d%9'%1tNJI%5A(sRJ)ZjRJb !Z Vk)R()KJ2$ZK9ZjBJRkuRRIZm-Zk-bl%ZkZL[K-bKb1 npHqBCV!2J9眃B!R1砃B!DJ1會B!1 B1B!R: PJ RJBRJ !B(RJ)!J)RJ)%B(RJ)B(RJ)B(RJ)BRJ)RBRJ)RJ(!RJ)RJ %RJ)RJ)!RJ)RJ)#$"l4LQH h  "$OggS`(RëZM=97699:899GR?Kj U.>?$Sڈ;yw~wަFRH M4\Zh4ަv.;쌢%C&@xt-m2a+fe5/Xd-; _ R,@xވUw֙ml%)x%:Q0iRo~%.-N8Ӡ jVM,`T V l[{&+@` ǁya_H*?; 'x)0WŸGJ~ bI,EP56K@+A)+@ё3(UՎSxLy }>^ 4K xoBQt%U|6fr-`XGi]v 6x*CID34 q% I g-jg_,UW<P4έ:_u'{*(C!, \~J%h%W +bĴ?Ͽ@D@ݕ=G,OKАLDm*nw <I;:,Dm*D W<jp_7#_yoCjNVR*FKn^r ^%%`\:Pr%ٖ[.çZ 51$ͻ^L|8'ٕ dgٕ d PɷjzDBH!ì iDu. BsԥoN`.&L$?cqV Ϯ:D氕?m(yy1sXt ٱ!(؀#s`l-dWd!=0?8qqq'を 1- u9 ;iptux-0.7.4/src/000077500000000000000000000000001323207530100134565ustar00rootroot00000000000000iptux-0.7.4/src/CMakeLists.txt000066400000000000000000000014731323207530100162230ustar00rootroot00000000000000find_package(GTest) if(NOT GTEST_FOUND) configure_file(googletest-download/CMakeLists.txt.in googletest-download/CMakeLists.txt) execute_process(COMMAND "${CMAKE_COMMAND}" -G "${CMAKE_GENERATOR}" . WORKING_DIRECTORY "${CMAKE_BINARY_DIR}/src/googletest-download" ) execute_process(COMMAND "${CMAKE_COMMAND}" --build . WORKING_DIRECTORY "${CMAKE_BINARY_DIR}/src/googletest-download" ) # Prevent GoogleTest from overriding our compiler/linker options # when building with Visual Studio set(gtest_force_shared_crt ON CACHE BOOL "" FORCE) # Add googletest directly to our build. This adds # the following targets: gtest, gtest_main, gmock # and gmock_main add_subdirectory("${CMAKE_BINARY_DIR}/src/googletest-src" "${CMAKE_BINARY_DIR}/src/googletest-build") endif() add_subdirectory(iptux) add_subdirectory(main) iptux-0.7.4/src/googletest-download/000077500000000000000000000000001323207530100174375ustar00rootroot00000000000000iptux-0.7.4/src/googletest-download/CMakeLists.txt.in000066400000000000000000000007211323207530100226040ustar00rootroot00000000000000cmake_minimum_required(VERSION 2.8.2) project(googletest-download NONE) include(ExternalProject) ExternalProject_Add(googletest URL https://github.com/google/googletest/archive/release-1.8.0.tar.gz URL_HASH SHA1=e7e646a6204638fe8e87e165292b8dd9cd4c36ed SOURCE_DIR "${CMAKE_BINARY_DIR}/src/googletest-src" BINARY_DIR "${CMAKE_BINARY_DIR}/src/googletest-build" CONFIGURE_COMMAND "" BUILD_COMMAND "" INSTALL_COMMAND "" TEST_COMMAND "" ) iptux-0.7.4/src/iptux/000077500000000000000000000000001323207530100146275ustar00rootroot00000000000000iptux-0.7.4/src/iptux/AnalogFS.cpp000066400000000000000000000120561323207530100167710ustar00rootroot00000000000000// // C++ Implementation: AnalogFS // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "AnalogFS.h" #include #include #include #include "iptux/ipmsg.h" #include "iptux/output.h" #include "iptux/utils.h" using namespace std; namespace iptux { /** * 类构造函数. */ AnalogFS::AnalogFS() { if (!::getcwd(path, MAX_PATHLEN)) strcpy(path, "/"); } /** * 类析构函数. */ AnalogFS::~AnalogFS() {} /** * 更改当前工作目录. * @param dir 目录路径 * @return 成功与否 */ int AnalogFS::chdir(const char *dir) { size_t len; char *ptr; if (strcmp(dir, ".") == 0) return 0; if (*dir != '/') { if (strcmp(dir, "..") == 0) { ptr = strrchr(path, '/'); if (ptr != path) *ptr = '\0'; } else { len = strlen(path); ptr = (char *)(*(path + 1) != '\0' ? "/" : ""); snprintf(path + len, MAX_PATHLEN - len, "%s%s", ptr, dir); } } else snprintf(path, MAX_PATHLEN, "%s", dir); return 0; } int AnalogFS::open(const char *fn, int flags) { return open(fn, flags, 0); } /** * 打开文件. * @param fn 文件路径 * @param flags as in open() * @param ... as in open() * @return 文件描述符 */ int AnalogFS::open(const char *fn, int flags, mode_t mode) { char tpath[MAX_PATHLEN]; char *tfn; int fd; strcpy(tpath, path); mergepath(tpath, fn); if ((flags & O_ACCMODE) == O_WRONLY) { tfn = assert_filename_inexist(tpath); if ((fd = ::open(tfn, flags, mode)) == -1) pwarning(_("Open() file \"%s\" failed, %s"), tfn, strerror(errno)); g_free(tfn); } else { if ((fd = ::open(tpath, flags, mode)) == -1) pwarning(_("Open() file \"%s\" failed, %s"), tpath, strerror(errno)); } return fd; } /** * 获取文件状态. * @param fn 文件路径 * @param st a stat64 struct * @return 成功与否 */ int AnalogFS::stat(const char *fn, struct ::stat *st) { char tpath[MAX_PATHLEN]; int result; strcpy(tpath, path); mergepath(tpath, fn); if ((result = ::stat(tpath, st)) != 0) { pwarning(_("Stat64() file \"%s\" failed, %s"), tpath, strerror(errno)); } return result; } /** * 创建新的目录. * @param dir 目录路径 * @param mode as in mkdir() * @return 成功与否 */ int AnalogFS::mkdir(const char *dir, mode_t mode) { char tpath[MAX_PATHLEN]; int result; strcpy(tpath, path); mergepath(tpath, dir); if (::access(tpath, F_OK) == 0) return 0; if ((result = ::mkdir(tpath, mode)) != 0) pwarning(_("Mkdir() directory \"%s\" failed, %s"), tpath, strerror(errno)); return result; } /** * 获取目录总大小. * @param dir_name 目录路径 * @return 目录大小 */ int64_t AnalogFS::ftwsize(const char *dir_name) { // 由于系统中存在使用此方法读取文件的大小的调用,因此需要判断文件dir_name是文件还是目录 struct stat st; int result = stat(dir_name, &st); if (result != 0) { // Fail to determine file type, return 0 (判断文件类型失败,直接返回 0) pwarning(_("stat file \"%s\" failed: %s"), dir_name, strerror(errno)); return 0; } if (S_ISREG(st.st_mode)) { return st.st_size; } if (!S_ISDIR(st.st_mode)) { pwarning(_("path %s is not file or directory: st_mode(%x)"), dirname, st.st_mode); return 0; } // 到了这里就一定是目录了 DIR *dir = opendir(dir_name); if (dir == NULL) { pwarning(_("opendir on \"%s\" failed: %s"), dir_name, strerror(errno)); return 0; } struct dirent *dirt; int64_t sumsize = 0; while ((dirt = readdir(dir))) { if (strcmp(dirt->d_name, ".") == 0) { continue; } if (strcmp(dirt->d_name, "..") == 0) { continue; } char tpath[MAX_PATHLEN]; strcpy(tpath, dir_name); mergepath(tpath, dirt->d_name); struct stat st; if (stat(tpath, &st) == -1) { continue; } if (S_ISDIR(st.st_mode)) { sumsize += ftwsize(tpath); } else if (S_ISREG(st.st_mode)) { sumsize += st.st_size; } else { // ignore other files } } return sumsize; } /** * 打开目录. * @param dir 目录路径 * @return DIR */ DIR *AnalogFS::opendir(const char *dir) { char tpath[MAX_PATHLEN]; DIR *dirs; strcpy(tpath, path); mergepath(tpath, dir); if (!(dirs = ::opendir(tpath))) pwarning(_("Opendir() directory \"%s\" failed, %s"), tpath, strerror(errno)); return dirs; } /** * 合并路径. * @param tpath[] 基路径 * @param npath 需要被合并的路径 * @return 成功与否 */ int AnalogFS::mergepath(char tpath[], const char *npath) { size_t len; char *ptr; if (strcmp(npath, ".") == 0) return 0; if (*npath != '/') { if (strcmp(npath, "..") == 0) { ptr = strrchr(tpath, '/'); if (ptr != tpath) *ptr = '\0'; } else { len = strlen(tpath); ptr = (char *)(*(tpath + 1) != '\0' ? "/" : ""); snprintf(tpath + len, MAX_PATHLEN - len, "%s%s", ptr, npath); } } else snprintf(tpath, MAX_PATHLEN, "%s", npath); return 0; } } // namespace iptux iptux-0.7.4/src/iptux/AnalogFS.h000066400000000000000000000017211323207530100164330ustar00rootroot00000000000000// // C++ Interface: AnalogFS // // Description: // 虚拟文件系统,接口函数使用方法尽量与库函数相同 // 意义在于使用此类操作文件可保证多线程安全 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_ANALOGFS_H #define IPTUX_ANALOGFS_H #include #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class AnalogFS { public: AnalogFS(); ~AnalogFS(); int chdir(const char *dir); int open(const char *fn, int flags); int open(const char *fn, int flags, mode_t mode); int stat(const char *fn, struct ::stat *st); int mkdir(const char *dir, mode_t mode); int64_t ftwsize(const char *dir); DIR *opendir(const char *dir); private: int mergepath(char tpath[], const char *npath); char path[MAX_PATHLEN]; //当前工作路径 public: inline char *cwd() { return path; } }; } // namespace iptux #endif iptux-0.7.4/src/iptux/CMakeLists.txt000066400000000000000000000023021323207530100173640ustar00rootroot00000000000000pkg_check_modules (IPTUX REQUIRED glib-2.0>=2.32.0 gthread-2.0>=2.14.0 gtk+-2.0>=2.16.0 jsoncpp>=1.0) include_directories("${PROJECT_SOURCE_DIR}/src" "${PROJECT_BINARY_DIR}/src" "${IPTUX_INCLUDE_DIRS}") link_libraries("${IPTUX_LIBRARIES}") link_libraries("${Intl_LIBRARIES}") if(GST_FOUND) include_directories("${GST_INCLUDE_DIRS}") link_libraries("${GST_LIBRARIES}") endif(GST_FOUND) add_library(iptux STATIC AnalogFS.cpp callback.cpp Command.cpp CoreThread.cpp DataSettings.cpp DetectPal.cpp dialog.cpp DialogBase.cpp DialogGroup.cpp DialogPeer.cpp HelpDialog.cpp IptuxConfig.cpp LogSystem.cpp MainWindow.cpp mess.cpp output.cpp ProgramData.cpp RecvFile.cpp RecvFileData.cpp RevisePal.cpp SendFile.cpp SendFileData.cpp ShareFile.cpp SoundSystem.cpp StatusIcon.cpp support.cpp TcpData.cpp UdpData.cpp utils.cpp wrapper.cpp WindowConfig.cpp ) add_executable(libiptux_test IptuxConfigTest.cpp UtilsTest.cpp TestMain.cpp ) if(GTEST_FOUND) include_directories(${GTEST_INCLUDE_DIRS}) target_link_libraries(libiptux_test ${GTEST_BOTH_LIBRARIES} iptux pthread) else() target_link_libraries(libiptux_test gtest iptux) endif() add_test(NAME libiptux_test COMMAND libiptux_test) iptux-0.7.4/src/iptux/Command.cpp000066400000000000000000000406121323207530100167140ustar00rootroot00000000000000// // C++ Implementation: Command // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "Command.h" #include #include #include #include "iptux/CoreThread.h" #include "iptux/ProgramData.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/support.h" #include "iptux/utils.h" #include "iptux/wrapper.h" using namespace std; namespace iptux { uint32_t Command::packetn = 1; /** * 类构造函数. */ Command::Command() : size(0) {} /** * 类析构函数. */ Command::~Command() {} /** * 向局域网所有计算机广播上线信息. * @param sock udp socket */ void Command::BroadCast(int sock) { struct sockaddr_in addr; GSList *list, *tlist; CreateCommand(IPMSG_ABSENCEOPT | IPMSG_BR_ENTRY, g_progdt->nickname.c_str()); ConvertEncode(g_progdt->encode); CreateIptuxExtra(g_progdt->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); tlist = list = get_sys_broadcast_addr(sock); while (tlist) { addr.sin_addr.s_addr = GPOINTER_TO_UINT(tlist->data); sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); g_usleep(9999); tlist = g_slist_next(tlist); } g_slist_free(list); } /** * 向局域网某些计算机单独发送上线信息. * @param sock udp socket */ void Command::DialUp(int sock) { struct sockaddr_in addr; in_addr_t startip, endip, ipv4; NetSegment *pns; GSList *list, *tlist; CreateCommand(IPMSG_DIALUPOPT | IPMSG_ABSENCEOPT | IPMSG_BR_ENTRY, g_progdt->nickname.c_str()); ConvertEncode(g_progdt->encode); CreateIptuxExtra(g_progdt->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); //与某些代码片段的获取网段描述相冲突,必须复制出来使用 g_progdt->Lock(); list = g_progdt->CopyNetSegment(); g_progdt->Unlock(); tlist = list; while (tlist) { pns = (NetSegment *)tlist->data; inet_pton(AF_INET, pns->startip, &startip); startip = ntohl(startip); inet_pton(AF_INET, pns->endip, &endip); endip = ntohl(endip); ipv4_order(&startip, &endip); ipv4 = startip; while (ipv4 <= endip) { addr.sin_addr.s_addr = htonl(ipv4); sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); g_usleep(999); ipv4++; } tlist = g_slist_next(tlist); } for (tlist = list; tlist; tlist = g_slist_next(tlist)) delete (NetSegment *)tlist->data; g_slist_free(list); } /** * 回复好友本人在线. * @param sock udp socket * @param pal class PalInfo */ void Command::SendAnsentry(int sock, PalInfo *pal) { struct sockaddr_in addr; CreateCommand(IPMSG_ABSENCEOPT | IPMSG_ANSENTRY, g_progdt->nickname.c_str()); ConvertEncode(pal->encode); CreateIptuxExtra(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 通告好友本人下线. * @param sock udp socket * @param pal class PalInfo */ void Command::SendExit(int sock, PalInfo *pal) { struct sockaddr_in addr; CreateCommand(IPMSG_DIALUPOPT | IPMSG_BR_EXIT, NULL); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 通告好友本人个人信息已变. * @param sock udp socket * @param pal class PalInfo */ void Command::SendAbsence(int sock, PalInfo *pal) { struct sockaddr_in addr; CreateCommand(IPMSG_ABSENCEOPT | IPMSG_BR_ABSENCE, g_progdt->nickname.c_str()); ConvertEncode(pal->encode); CreateIptuxExtra(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 尝试着给某计算机发送一个上线信息数据包. * @param sock udp socket * @param ipv4 ipv4 address */ void Command::SendDetectPacket(int sock, in_addr_t ipv4) { struct sockaddr_in addr; CreateCommand(IPMSG_DIALUPOPT | IPMSG_ABSENCEOPT | IPMSG_BR_ENTRY, g_progdt->nickname.c_str()); ConvertEncode(g_progdt->encode); CreateIptuxExtra(g_progdt->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 给好友发送消息. * @param sock udp socket * @param pal class PalInfo * @param msg 消息数据 */ void Command::SendMessage(int sock, PalInfo *pal, const char *msg) { struct sockaddr_in addr; uint32_t packetno; uint8_t count; pal->rpacketn = packetno = packetn; //此数据包需要检验回复 CreateCommand(IPMSG_SENDCHECKOPT | IPMSG_SENDMSG, msg); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; count = 0; do { sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); g_usleep(1000000); count++; } while (pal->rpacketn == packetno && count < MAX_RETRYTIMES); if (pal->rpacketn == packetno) FeedbackError(pal, GROUP_BELONG_TYPE_REGULAR, _("Your pal didn't receive the packet. " "He or she is offline maybe.")); } /** * 回复已收到消息. * @param sock udp socket * @param pal class PalInfo * @param packetno 好友消息的包编号 */ void Command::SendReply(int sock, PalInfo *pal, uint32_t packetno) { char packetstr[11]; // 10 +1 =11 struct sockaddr_in addr; snprintf(packetstr, 11, "%" PRIu32, packetno); CreateCommand(IPMSG_SENDCHECKOPT | IPMSG_RECVMSG, packetstr); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 群发消息(被其他函数调用). * @param sock udp socket * @param pal class PalInfo * @param msg 消息数据 */ void Command::SendGroupMsg(int sock, PalInfo *pal, const char *msg) { struct sockaddr_in addr; CreateCommand(IPMSG_BROADCASTOPT | IPMSG_SENDMSG, msg); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 发送群组消息(被其他函数调用). * @param sock udp socket * @param pal class PalInfo * @param opttype 命令额外选项 * @param msg 消息数据 */ void Command::SendUnitMsg(int sock, PalInfo *pal, uint32_t opttype, const char *msg) { struct sockaddr_in addr; CreateCommand(opttype | IPTUX_SENDMSG, msg); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 向好友请求文件数据. * @param sock tcp socket * @param pal class PalInfo * @param packetno 好友消息的包编号 * @param fileid 文件ID标识 * @param offset 文件偏移量 * @return 消息发送成功与否 */ bool Command::SendAskData(int sock, PalInfo *pal, uint32_t packetno, uint32_t fileid, int64_t offset) { char attrstr[35]; // 8+1+8+1+16 +1 =35 struct sockaddr_in addr; const char *iptuxstr = "iptux"; snprintf(attrstr, 35, "%" PRIx32 ":%" PRIx32 ":%" PRIx64, packetno, fileid, offset); // IPMSG和Feiq的命令字段都是只有IPMSG_GETFILEDATA,使用(IPMSG_FILEATTACHOPT | // IPMSG_GETFILEDATA) //会产生一些潜在的不兼容问题,所以在发往非iptux时只使用IPMSG_GETFILEDATA if (strstr(pal->version, iptuxstr)) CreateCommand(IPMSG_FILEATTACHOPT | IPMSG_GETFILEDATA, attrstr); else CreateCommand(IPMSG_GETFILEDATA, attrstr); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; if (((connect(sock, (struct sockaddr *)&addr, sizeof(addr)) == -1) && (errno != EINTR)) || (xwrite(sock, buf, size) == -1)) return false; return true; } /** * 向好友请求目录文件. * @param sock tcp socket * @param pal class PalInfo * @param packetno 好友消息的包编号 * @param fileid 文件ID标识 * @return 消息发送成功与否 */ bool Command::SendAskFiles(int sock, PalInfo *pal, uint32_t packetno, uint32_t fileid) { char attrstr[20]; // 8+1+8+1+1 +1 =20 struct sockaddr_in addr; snprintf(attrstr, 20, "%" PRIx32 ":%" PRIx32 ":0", packetno, fileid); //兼容LanQQ软件 CreateCommand(IPMSG_FILEATTACHOPT | IPMSG_GETDIRFILES, attrstr); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; if (((connect(sock, (struct sockaddr *)&addr, sizeof(addr)) == -1) && (errno != EINTR)) || (xwrite(sock, buf, size) == -1)) return false; return true; } /** * 向好友请求共享文件信息. * @param sock udp socket * @param pal class PalInfo * @param opttype 命令额外选项 * @param attach 附加数据,即密码 */ void Command::SendAskShared(int sock, PalInfo *pal, uint32_t opttype, const char *attach) { struct sockaddr_in addr; CreateCommand(opttype | IPTUX_ASKSHARED, attach); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 向好友发送文件信息. * @param sock udp socket * @param pal class PalInfo * @param opttype 命令额外选项 * @param extra 扩展数据,即文件信息 */ void Command::SendFileInfo(int sock, PalInfo *pal, uint32_t opttype, const char *extra) { struct sockaddr_in addr; CreateCommand(opttype | IPMSG_FILEATTACHOPT | IPMSG_SENDMSG, NULL); ConvertEncode(pal->encode); CreateIpmsgExtra(extra, pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 发送本人的头像数据. * @param sock udp socket * @param pal class PalInfo */ void Command::SendMyIcon(int sock, PalInfo *pal) { struct sockaddr_in addr; CreateCommand(IPTUX_SENDICON, NULL); ConvertEncode(pal->encode); CreateIconExtra(); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 发送本人的签名信息. * @param sock udp socket * @param pal class PalInfo */ void Command::SendMySign(int sock, PalInfo *pal) { struct sockaddr_in addr; CreateCommand(IPTUX_SENDSIGN, g_progdt->sign.c_str()); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; sendto(sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)); } /** * 发送底层数据(即发送为最终用户所不能察觉的文件数据). * @param sock tcp socket * @param pal class PalInfo * @param opttype 命令额外选项 * @param path 文件路径 */ void Command::SendSublayer(int sock, PalInfo *pal, uint32_t opttype, const char *path) { struct sockaddr_in addr; int fd; CreateCommand(opttype | IPTUX_SENDSUBLAYER, NULL); ConvertEncode(pal->encode); bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(IPTUX_DEFAULT_PORT); addr.sin_addr.s_addr = pal->ipv4; if (((connect(sock, (struct sockaddr *)&addr, sizeof(addr)) == -1) && (errno != EINTR)) || (xwrite(sock, buf, size) == -1) || ((fd = open(path, O_RDONLY)) == -1)) return; SendSublayerData(sock, fd); close(fd); } /** * 回馈错误消息. * @param pal class PalInfo * @param btype 消息归属类型 * @param error 错误串 */ void Command::FeedbackError(PalInfo *pal, GroupBelongType btype, const char *error) { MsgPara para; ChipData *chip; /* 构建消息封装包 */ para.pal = pal; para.stype = MESSAGE_SOURCE_TYPE_ERROR; para.btype = btype; chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_STRING; chip->data = g_strdup(error); para.dtlist = g_slist_append(NULL, chip); /* 交给某人处理吧 */ g_cthrd->InsertMessage(¶); } /** * 将文件描述符数据写入网络套接口. * @param sock tcp socket * @param fd file descriptor */ void Command::SendSublayerData(int sock, int fd) { ssize_t len; do { if ((len = xread(fd, buf, MAX_UDPLEN)) <= 0) break; if ((len = xwrite(sock, buf, len)) <= 0) break; } while (1); } /** * 将缓冲区中的字符串转换为指定的编码. * @param encode 字符集编码 */ void Command::ConvertEncode(const string &encode) { char *ptr; if (encode.empty()) { return; } if (strcasecmp(encode.c_str(), "utf-8") != 0 && (ptr = convert_encode(buf, encode.c_str(), "utf-8"))) { size = strlen(ptr) + 1; memcpy(buf, ptr, size); g_free(ptr); } } /** * 创建命令数据. * @param command 命令字 * @param attach 附加数据 */ void Command::CreateCommand(uint32_t command, const char *attach) { const gchar *env; char *ptr; snprintf(buf, MAX_UDPLEN, "%s", IPTUX_VERSION); size = strlen(buf); ptr = buf + size; snprintf(ptr, MAX_UDPLEN - size, ":%" PRIu32, packetn); packetn++; size += strlen(ptr); ptr = buf + size; env = g_get_user_name(); snprintf(ptr, MAX_UDPLEN - size, ":%s", env); size += strlen(ptr); ptr = buf + size; env = g_get_host_name(); snprintf(ptr, MAX_UDPLEN - size, ":%s", env); size += strlen(ptr); ptr = buf + size; if (command == IPMSG_GETFILEDATA) snprintf(ptr, MAX_UDPLEN - size, ":%d", command); else snprintf(ptr, MAX_UDPLEN - size, ":%" PRIu32, command); size += strlen(ptr); ptr = buf + size; snprintf(ptr, MAX_UDPLEN - size, ":%s", attach ? attach : ""); size += strlen(ptr) + 1; } /** * 创建ipmsg的扩展数据(即文件信息). * @param extra 扩展数据 * @param encode 字符集编码 */ void Command::CreateIpmsgExtra(const char *extra, const char *encode) { char *pptr, *ptr; pptr = buf + size; if (encode && strcasecmp(encode, "utf-8") != 0 && (ptr = convert_encode(extra, encode, "utf-8"))) { snprintf(pptr, MAX_UDPLEN - size, "%s", ptr); g_free(ptr); } else snprintf(pptr, MAX_UDPLEN - size, "%s", extra); if ((ptr = strrchr(pptr, '\a'))) *(ptr + 1) = '\0'; size += strlen(pptr) + 1; } /** * 创建iptux程序独有的扩展数据. * @param encode 字符集编码 */ void Command::CreateIptuxExtra(const string &encode) { char *pptr, *ptr; pptr = buf + size; if (!encode.empty() && strcasecmp(encode.c_str(), "utf-8") != 0 && (ptr = convert_encode(g_progdt->mygroup.c_str(), encode.c_str(), "utf-8"))) { snprintf(pptr, MAX_UDPLEN - size, "%s", ptr); g_free(ptr); } else snprintf(pptr, MAX_UDPLEN - size, "%s", g_progdt->mygroup.c_str()); size += strlen(pptr) + 1; pptr = buf + size; snprintf(pptr, MAX_UDPLEN - size, "%s", g_progdt->myicon.c_str()); size += strlen(pptr) + 1; pptr = buf + size; snprintf(pptr, MAX_UDPLEN - size, "utf-8"); size += strlen(pptr) + 1; } /** * 创建个人头像的扩展数据. */ void Command::CreateIconExtra() { const gchar *env; char path[MAX_PATHLEN]; ssize_t len; int fd; env = g_get_user_config_dir(); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/my-icon", env); if ((fd = open(path, O_RDONLY)) == -1) return; len = xread(fd, buf + size, MAX_UDPLEN - size); close(fd); if (len != -1) size += len; } } // namespace iptuxiptux-0.7.4/src/iptux/Command.h000066400000000000000000000040361323207530100163610ustar00rootroot00000000000000// // C++ Interface: Command // // Description: // 创建命令并发送 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_COMMAND_H #define IPTUX_COMMAND_H #include #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class Command { public: Command(); ~Command(); void BroadCast(int sock); void DialUp(int sock); void SendAnsentry(int sock, PalInfo *pal); void SendExit(int sock, PalInfo *pal); void SendAbsence(int sock, PalInfo *pal); void SendDetectPacket(int sock, in_addr_t ipv4); void SendMessage(int sock, PalInfo *pal, const char *msg); void SendReply(int sock, PalInfo *pal, uint32_t packetno); void SendGroupMsg(int sock, PalInfo *pal, const char *msg); void SendUnitMsg(int sock, PalInfo *pal, uint32_t opttype, const char *msg); bool SendAskData(int sock, PalInfo *pal, uint32_t packetno, uint32_t fileid, int64_t offset); bool SendAskFiles(int sock, PalInfo *pal, uint32_t packetno, uint32_t fileid); void SendAskShared(int sock, PalInfo *pal, uint32_t opttype, const char *attach); void SendFileInfo(int sock, PalInfo *pal, uint32_t opttype, const char *extra); void SendMyIcon(int sock, PalInfo *pal); void SendMySign(int sock, PalInfo *pal); void SendSublayer(int sock, PalInfo *pal, uint32_t opttype, const char *path); private: void FeedbackError(PalInfo *pal, GroupBelongType btype, const char *error); void SendSublayerData(int sock, int fd); void ConvertEncode(const std::string &encode); void CreateCommand(uint32_t command, const char *attach); void CreateIpmsgExtra(const char *extra, const char *encode); void CreateIptuxExtra(const std::string &encode); void CreateIconExtra(); size_t size; //当前已使用缓冲区的长度 char buf[MAX_UDPLEN]; //数据缓冲区 static uint32_t packetn; //包编号 public: inline uint32_t &Packetn() { return packetn; } }; } // namespace iptux #endif iptux-0.7.4/src/iptux/CoreThread.cpp000066400000000000000000001041731323207530100173610ustar00rootroot00000000000000// // C++ Implementation: CoreThread // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "CoreThread.h" #include #include #include "iptux/Command.h" #include "iptux/LogSystem.h" #include "iptux/MainWindow.h" #include "iptux/ProgramData.h" #include "iptux/TcpData.h" #include "iptux/UdpData.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/output.h" #include "iptux/support.h" #include "iptux/utils.h" using namespace std; namespace iptux { static const char *CONFIG_SHARED_FILE_LIST = "shared_file_list"; static const char *CONFIG_ACCESS_SHARED_LIMIT = "access_shared_limit"; /** * 类构造函数. */ CoreThread::CoreThread(IptuxConfig &config) : config(config), tcpsock(-1), udpsock(-1), server(true), pallist(nullptr), rgllist(NULL), sgmlist(NULL), grplist(NULL), brdlist(NULL), blacklist(NULL), pbn(1), prn(MAX_SHAREDFILE), pblist(NULL), prlist(NULL), ecsList(NULL) { g_queue_init(&msgline); pthread_mutex_init(&mutex, NULL); } /** * 类析构函数. */ CoreThread::~CoreThread() { ClearSublayer(); } /** * 程序核心入口,主要任务服务将在此开启. */ void CoreThread::CoreThreadEntry() { pthread_t pid; /* 初始化底层数据 */ InitSublayer(); /* 开启UDP监听服务 */ pthread_create(&pid, NULL, ThreadFunc(RecvUdpData), this); pthread_detach(pid); /* 开启TCP监听服务 */ pthread_create(&pid, NULL, ThreadFunc(RecvTcpData), this); pthread_detach(pid); /* 定时扫描处理程序内部任务 */ timerid = gdk_threads_add_timeout(500, GSourceFunc(WatchCoreStatus), this); /* 通知所有计算机本大爷上线啦 */ pthread_create(&pid, NULL, ThreadFunc(SendNotifyToAll), this); } /** * 写出共享文件数据. * @note 与可能修改链表的代码段串行执行,没有加锁的必要 */ void CoreThread::WriteSharedData() { GSList *tlist; /* 获取共享文件链表 */ vector sharedFileList; tlist = pblist; while (tlist) { sharedFileList.push_back(string(((FileInfo *)tlist->data)->filepath)); tlist = g_slist_next(tlist); } /* 写出数据 */ config.SetStringList(CONFIG_SHARED_FILE_LIST, sharedFileList); if (!passwd.empty()) { config.SetString(CONFIG_ACCESS_SHARED_LIMIT, passwd); } config.Save(); } /** * 获取好友链表. * @return 好友链表 */ GSList *CoreThread::GetPalList() { return pallist; } /** * 插入消息(UI线程安全). * @param para 消息参数封装包 * @note 消息数据必须使用utf8编码 * @note (para->pal)不可为null * @note * 请不要关心函数内部实现,你只需要按照要求封装消息数据,然后扔给本函数处理就可以了, * 它会想办法将消息按照你所期望的格式插入到你所期望的TextBuffer,否则请发送Bug报告 */ void CoreThread::InsertMessage(MsgPara *para) { GroupInfo *grpinf; SessionAbstract *session; /* 启用UI线程安全保护 */ gdk_threads_enter(); /* 获取群组信息 */ switch (para->btype) { case GROUP_BELONG_TYPE_REGULAR: grpinf = GetPalRegularItem(para->pal); break; case GROUP_BELONG_TYPE_SEGMENT: grpinf = GetPalSegmentItem(para->pal); break; case GROUP_BELONG_TYPE_GROUP: grpinf = GetPalGroupItem(para->pal); break; case GROUP_BELONG_TYPE_BROADCAST: grpinf = GetPalBroadcastItem(para->pal); break; default: grpinf = NULL; break; } /* 如果群组存在则插入消息 */ /* 群组不存在是编程上的错误,请发送Bug报告 */ if (grpinf) { InsertMsgToGroupInfoItem(grpinf, para); if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->OnNewMessageComing(); } } /* 离开UI操作处理 */ gdk_threads_leave(); } /** * 插入消息到群组消息缓冲区(非UI线程安全). * @param grpinf 群组信息 * @param para 消息参数 */ void CoreThread::InsertMsgToGroupInfoItem(GroupInfo *grpinf, MsgPara *para) { GtkTextIter iter; GSList *tlist; gchar *data; tlist = para->dtlist; while (tlist) { data = ((ChipData *)tlist->data)->data; switch (((ChipData *)tlist->data)->type) { case MESSAGE_CONTENT_TYPE_STRING: InsertHeaderToBuffer(grpinf->buffer, para); gtk_text_buffer_get_end_iter(grpinf->buffer, &iter); gtk_text_buffer_insert(grpinf->buffer, &iter, "\n", -1); InsertStringToBuffer(grpinf->buffer, data); gtk_text_buffer_get_end_iter(grpinf->buffer, &iter); gtk_text_buffer_insert(grpinf->buffer, &iter, "\n", -1); g_lgsys->CommunicateLog(para, "[STRING]%s", data); break; case MESSAGE_CONTENT_TYPE_PICTURE: InsertPixbufToBuffer(grpinf->buffer, data); g_lgsys->CommunicateLog(para, "[PICTURE]%s", data); break; default: break; } tlist = g_slist_next(tlist); } } /** * 向局域网内所有计算机发送上线信息. * @param pcthrd 核心类 */ void CoreThread::SendNotifyToAll(CoreThread *pcthrd) { Command cmd; cmd.BroadCast(pcthrd->udpsock); cmd.DialUp(pcthrd->udpsock); } /** * 向好友发送iptux特有的数据. * @param pal class PalInfo */ void CoreThread::SendFeatureData(PalInfo *pal) { Command cmd; char path[MAX_PATHLEN]; const gchar *env; int sock; if (!g_progdt->sign.empty()) { cmd.SendMySign(g_cthrd->udpsock, pal); } env = g_get_user_config_dir(); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/%s", env, g_progdt->myicon.c_str()); if (access(path, F_OK) == 0) cmd.SendMyIcon(g_cthrd->udpsock, pal); snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH "/photo", env); if (access(path, F_OK) == 0) { if ((sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) { pop_error(_("Fatal Error!!\nFailed to create new socket!\n%s"), strerror(errno)); exit(1); } cmd.SendSublayer(sock, pal, IPTUX_PHOTOPICOPT, path); close(sock); } } /** * 发送通告本计算机下线的信息. * @param pal class PalInfo */ void CoreThread::SendBroadcastExit(PalInfo *pal) { Command cmd; cmd.SendExit(g_cthrd->udpsock, pal); } /** * 更新本大爷的个人信息. */ void CoreThread::UpdateMyInfo() { Command cmd; pthread_t pid; PalInfo *pal; GSList *tlist; pthread_mutex_lock(&g_cthrd->mutex); tlist = g_cthrd->pallist; while (tlist) { pal = (PalInfo *)tlist->data; if (FLAG_ISSET(pal->flags, 1)) cmd.SendAbsence(g_cthrd->udpsock, pal); if (FLAG_ISSET(pal->flags, 1) && FLAG_ISSET(pal->flags, 0)) { pthread_create(&pid, NULL, ThreadFunc(SendFeatureData), pal); pthread_detach(pid); } tlist = g_slist_next(tlist); } pthread_mutex_unlock(&g_cthrd->mutex); } /** * 从好友链表中移除所有好友数据(非UI线程安全). * @note 鉴于好友链表成员不能被删除,所以将成员改为下线标记即可 */ void CoreThread::ClearAllPalFromList() { SessionAbstract *session; GroupInfo *grpinf; PalInfo *pal; GSList *tlist; /* 清除所有好友的在线标志 */ tlist = pallist; while (tlist) { pal = (PalInfo *)tlist->data; FLAG_CLR(pal->flags, 1); tlist = g_slist_next(tlist); } /* 清空常规模式下所有群组的成员 */ tlist = rgllist; while (tlist) { grpinf = (GroupInfo *)tlist->data; g_slist_free(grpinf->member); grpinf->member = NULL; if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->ClearAllPalData(); } tlist = g_slist_next(tlist); } /* 清空网段模式下所有群组的成员 */ tlist = sgmlist; while (tlist) { grpinf = (GroupInfo *)tlist->data; g_slist_free(grpinf->member); grpinf->member = NULL; if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->ClearAllPalData(); } tlist = g_slist_next(tlist); } /* 清空分组模式下所有群组的成员 */ tlist = grplist; while (tlist) { grpinf = (GroupInfo *)tlist->data; g_slist_free(grpinf->member); grpinf->member = NULL; if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->ClearAllPalData(); } tlist = g_slist_next(tlist); } /* 清空广播模式下所有群组的成员 */ tlist = brdlist; while (tlist) { grpinf = (GroupInfo *)tlist->data; g_slist_free(grpinf->member); grpinf->member = NULL; if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->ClearAllPalData(); } tlist = g_slist_next(tlist); } } /** * 从好友链表中获取指定的好友信息数据. * @param ipv4 ipv4 * @return 好友信息数据 */ PalInfo *CoreThread::GetPalFromList(in_addr_t ipv4) { GSList *tlist; tlist = pallist; while (tlist) { if (((PalInfo *)tlist->data)->ipv4 == ipv4) break; tlist = g_slist_next(tlist); } return (PalInfo *)(tlist ? tlist->data : NULL); } /** * 查询好友链表中是否已经存在此IP地址的信息数据. * @param ipv4 ipv4 * @return 存在与否 */ bool CoreThread::ListContainPal(in_addr_t ipv4) { GSList *tlist; tlist = pallist; while (tlist) { if (((PalInfo *)tlist->data)->ipv4 == ipv4) break; tlist = g_slist_next(tlist); } return tlist; } /** * 从好友链表中删除指定的好友信息数据(非UI线程安全). * @param ipv4 ipv4 * @note 鉴于好友链表成员不能被删除,所以将成员改为下线标记即可; * 鉴于群组中只能包含在线的好友,所以若某群组中包含了此好友,则必须从此群组中删除此好友 */ void CoreThread::DelPalFromList(in_addr_t ipv4) { PalInfo *pal; GroupInfo *grpinf; /* 获取好友信息数据,并将其置为下线状态 */ if (!(pal = GetPalFromList(ipv4))) return; FLAG_CLR(pal->flags, 1); /* 从群组中移除好友 */ if ((grpinf = GetPalRegularItem(pal))) DelPalFromGroupInfoItem(grpinf, pal); if ((grpinf = GetPalSegmentItem(pal))) DelPalFromGroupInfoItem(grpinf, pal); if ((grpinf = GetPalGroupItem(pal))) DelPalFromGroupInfoItem(grpinf, pal); if ((grpinf = GetPalBroadcastItem(pal))) DelPalFromGroupInfoItem(grpinf, pal); } /** * 通告指定的好友信息数据已经被更新(非UI线程安全). * @param ipv4 ipv4 * @note 什么时候会用到?1、好友更新个人资料;2、好友下线后又上线了 * @note 鉴于群组中必须包含所有属于自己的成员,移除不属于自己的成员, * 所以好友信息更新后应该重新调整群组成员; * @note 群组中被更新的成员信息也应该在界面上做出相应更新 */ void CoreThread::UpdatePalToList(in_addr_t ipv4) { PalInfo *pal; GroupInfo *grpinf; SessionAbstract *session; /* 如果好友链表中不存在此好友,则视为程序设计出错 */ if (!(pal = GetPalFromList(ipv4))) return; FLAG_SET(pal->flags, 1); /* 更新好友所在的群组,以及它在UI上的信息 */ /*/* 更新常规模式下的群组 */ if ((grpinf = GetPalRegularItem(pal))) { if (!g_slist_find(grpinf->member, pal)) { AttachPalToGroupInfoItem(grpinf, pal); } else if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->UpdatePalData(pal); } } else { if (!(grpinf = GetPalRegularItem(pal))) grpinf = AttachPalRegularItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } /*/* 更新网段模式下的群组 */ if ((grpinf = GetPalSegmentItem(pal))) { if (!g_slist_find(grpinf->member, pal)) { AttachPalToGroupInfoItem(grpinf, pal); } else if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->UpdatePalData(pal); } } else { if (!(grpinf = GetPalSegmentItem(pal))) grpinf = AttachPalSegmentItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } /*/* 更新分组模式下的群组 */ if ((grpinf = GetPalPrevGroupItem(pal))) { if (!pal->group || strcmp(grpinf->name, pal->group) != 0) { DelPalFromGroupInfoItem(grpinf, pal); if (!(grpinf = GetPalGroupItem(pal))) grpinf = AttachPalGroupItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } else if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->UpdatePalData(pal); } } else { if (!(grpinf = GetPalGroupItem(pal))) grpinf = AttachPalGroupItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } /*/* 更新广播模式下的群组 */ if ((grpinf = GetPalBroadcastItem(pal))) { if (!g_slist_find(grpinf->member, pal)) { AttachPalToGroupInfoItem(grpinf, pal); } else if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->UpdatePalData(pal); } } else { if (!(grpinf = GetPalBroadcastItem(pal))) grpinf = AttachPalBroadcastItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } } /** * 将好友信息数据加入到好友链表(非UI线程安全). * @param pal class PalInfo * @note 鉴于在线的好友必须被分配到它所属的群组,所以加入好友到好友链表的同时 * 也应该分配好友到相应的群组 */ void CoreThread::AttachPalToList(PalInfo *pal) { GroupInfo *grpinf; /* 将好友加入到好友链表 */ pallist = g_slist_append(pallist, pal); FLAG_SET(pal->flags, 1); /* 将好友加入到相应的群组 */ if (!(grpinf = GetPalRegularItem(pal))) grpinf = AttachPalRegularItem(pal); AttachPalToGroupInfoItem(grpinf, pal); if (!(grpinf = GetPalSegmentItem(pal))) grpinf = AttachPalSegmentItem(pal); AttachPalToGroupInfoItem(grpinf, pal); if (!(grpinf = GetPalGroupItem(pal))) grpinf = AttachPalGroupItem(pal); AttachPalToGroupInfoItem(grpinf, pal); if (!(grpinf = GetPalBroadcastItem(pal))) grpinf = AttachPalBroadcastItem(pal); AttachPalToGroupInfoItem(grpinf, pal); } /** * 获取(pal)在常规模式下的群组信息. * @param pal class PalInfo * @return 群组信息 */ GroupInfo *CoreThread::GetPalRegularItem(PalInfo *pal) { GSList *tlist; tlist = rgllist; while (tlist) { if (((GroupInfo *)tlist->data)->grpid == pal->ipv4) break; tlist = g_slist_next(tlist); } return (GroupInfo *)(tlist ? tlist->data : NULL); } /** * 获取(pal)在网段模式下的群组信息. * @param pal class PalInfo * @return 群组信息 */ GroupInfo *CoreThread::GetPalSegmentItem(PalInfo *pal) { GSList *tlist; char *name; GQuark grpid; /* 获取局域网网段ID */ name = ipv4_get_lan_name(pal->ipv4); grpid = g_quark_from_string(name ? name : _("Others")); g_free(name); tlist = sgmlist; while (tlist) { if (((GroupInfo *)tlist->data)->grpid == grpid) break; tlist = g_slist_next(tlist); } return (GroupInfo *)(tlist ? tlist->data : NULL); } /** * 获取(pal)在分组模式下的群组信息. * @param pal class PalInfo * @return 群组信息 */ GroupInfo *CoreThread::GetPalGroupItem(PalInfo *pal) { GSList *tlist; GQuark grpid; /* 获取组ID */ NO_OPERATION_C grpid = g_quark_from_string(pal->group ? pal->group : _("Others")); tlist = grplist; while (tlist) { if (((GroupInfo *)tlist->data)->grpid == grpid) break; tlist = g_slist_next(tlist); } return (GroupInfo *)(tlist ? tlist->data : NULL); } /** * 获取(pal)在广播模式下的群组信息. * @param pal class PalInfo * @return 群组信息 */ GroupInfo *CoreThread::GetPalBroadcastItem(PalInfo *pal) { return (GroupInfo *)(brdlist ? brdlist->data : NULL); } /** * 黑名单链表中是否包含此项. * @param ipv4 ipv4 * @return 是否包含 */ bool CoreThread::BlacklistContainItem(in_addr_t ipv4) { return g_slist_find(blacklist, GUINT_TO_POINTER(ipv4)); } /** * 加入此项到黑名单链表. * @param ipv4 ipv4 */ void CoreThread::AttachItemToBlacklist(in_addr_t ipv4) { blacklist = g_slist_append(blacklist, GUINT_TO_POINTER(ipv4)); } /** * 清空黑名单链表. */ void CoreThread::ClearBlacklist() { g_slist_free(blacklist); blacklist = NULL; } /** * 获取消息队列项总数. * @return 项数 */ guint CoreThread::GetMsglineItems() { return g_queue_get_length(&msgline); } /** * 查看消息队列首项. * @return 项 */ GroupInfo *CoreThread::GetMsglineHeadItem() { return (GroupInfo *)g_queue_peek_head(&msgline); } /** * 消息队列是否已经包含此项. * @param grpinf 项 * @return 是否包含 */ bool CoreThread::MsglineContainItem(GroupInfo *grpinf) { return g_queue_find(&msgline, grpinf); } /** * 压入项进消息队列. * @param grpinf 项 */ void CoreThread::PushItemToMsgline(GroupInfo *grpinf) { g_queue_push_tail(&msgline, grpinf); } /** * 弹出项从消息队列. * @param grpinf 项 */ void CoreThread::PopItemFromMsgline(GroupInfo *grpinf) { g_queue_remove(&msgline, grpinf); } /** * 附加文件信息到公有文件链表. * @param file 文件信息 */ void CoreThread::AttachFileToPublic(FileInfo *file) { pblist = g_slist_append(pblist, file); } /** * 从公有文件链表删除指定的文件. * @param fileid 文件ID */ void CoreThread::DelFileFromPublic(uint32_t fileid) { GSList *tlist; tlist = pblist; while (tlist) { if (((FileInfo *)tlist->data)->fileid == fileid) { delete (FileInfo *)tlist->data; pblist = g_slist_delete_link(pblist, tlist); break; } tlist = g_slist_next(tlist); } } /** * 清空公有文件链表. */ void CoreThread::ClearFileFromPublic() { for (GSList *tlist = pblist; tlist; tlist = g_slist_next(tlist)) delete (FileInfo *)tlist->data; g_slist_free(pblist); pblist = NULL; } /** * 获取公有文件链表指针. * @return 链表 */ GSList *CoreThread::GetPublicFileList() { return pblist; } /** * 附加文件信息到私有文件链表. * @param file 文件信息 */ void CoreThread::AttachFileToPrivate(FileInfo *file) { prlist = g_slist_append(prlist, file); } /** * 从私有文件链表删除指定的文件. * @param fileid 文件ID */ void CoreThread::DelFileFromPrivate(uint32_t fileid) { GSList *tlist; tlist = prlist; while (tlist) { if (((FileInfo *)tlist->data)->fileid == fileid) { delete (FileInfo *)tlist->data; prlist = g_slist_delete_link(prlist, tlist); break; } tlist = g_slist_next(tlist); } } /** * 清空私有文件链表. */ void CoreThread::ClearFileFromPrivate() { for (GSList *tlist = prlist; tlist; tlist = g_slist_next(tlist)) delete (FileInfo *)tlist->data; g_slist_free(prlist); prlist = NULL; } /** * 获取指定文件ID的文件信息. * @param fileid 文件ID * @return 文件信息 */ FileInfo *CoreThread::GetFileFromAll(uint32_t fileid) { GSList *tlist; tlist = fileid < MAX_SHAREDFILE ? pblist : prlist; while (tlist) { if (((FileInfo *)tlist->data)->fileid == fileid) break; tlist = g_slist_next(tlist); } return (FileInfo *)(tlist ? tlist->data : NULL); } /** * 获取指定文件包编号的文件信息. * @param PacketN 文件包ID * @return 文件信息 * 这个函数主要是为了兼容adroid版的信鸽(IPMSG),IPMSG把包编号转换为 * 16进制放在了本来应该是fileid的地方,在存放文件创建时间的地方放上了包内编号 * 所以在调用这个函数时,传给packageNum的是fileid, * 传的filectime实际上是包内编号 */ FileInfo *CoreThread::GetFileFromAllWithPacketN(uint32_t packageNum, uint32_t filectime) { GSList *tlist; tlist = prlist; while (tlist) { if ((((FileInfo *)tlist->data)->packetn == packageNum) && ((((FileInfo *)tlist->data)->filenum == filectime))) break; tlist = g_slist_next(tlist); } if (tlist != NULL) return (FileInfo *)(tlist ? tlist->data : NULL); tlist = pblist; while (tlist) { if ((((FileInfo *)tlist->data)->packetn == packageNum) && ((((FileInfo *)tlist->data)->filenum == filectime))) break; tlist = g_slist_next(tlist); } return (FileInfo *)(tlist ? tlist->data : NULL); } /** * 获取共享文件访问密码. * @return 密码字符串 */ const char *CoreThread::GetAccessPublicLimit() { return passwd.c_str(); } /** * 更新共享文件访问密码. * @param limit 密码字符串 */ void CoreThread::SetAccessPublicLimit(const char *limit) { if (limit == NULL) { passwd = ""; } else { passwd = string(limit); } } /** * 初始化底层数据. */ void CoreThread::InitSublayer() { InitThemeSublayerData(); ReadSharedData(); } /** * 清空底层数据. */ void CoreThread::ClearSublayer() { GSList *tlist; /** * @note 必须在发送下线信息之后才能关闭套接口. */ g_slist_foreach(pallist, GFunc(SendBroadcastExit), NULL); shutdown(tcpsock, SHUT_RDWR); shutdown(udpsock, SHUT_RDWR); server = false; for (tlist = pallist; tlist; tlist = g_slist_next(tlist)) delete (PalInfo *)tlist->data; g_slist_free(pallist); for (tlist = rgllist; tlist; tlist = g_slist_next(tlist)) delete (GroupInfo *)tlist->data; g_slist_free(rgllist); for (tlist = sgmlist; tlist; tlist = g_slist_next(tlist)) delete (GroupInfo *)tlist->data; g_slist_free(sgmlist); for (tlist = grplist; tlist; tlist = g_slist_next(tlist)) delete (GroupInfo *)tlist->data; g_slist_free(grplist); for (tlist = brdlist; tlist; tlist = g_slist_next(tlist)) delete (GroupInfo *)tlist->data; g_slist_free(brdlist); g_slist_free(blacklist); g_queue_clear(&msgline); for (tlist = pblist; tlist; tlist = g_slist_next(tlist)) delete (FileInfo *)tlist->data; g_slist_free(pblist); for (tlist = prlist; tlist; tlist = g_slist_next(tlist)) delete (FileInfo *)tlist->data; g_slist_free(prlist); for (tlist = ecsList; tlist; tlist = g_slist_next(tlist)) delete (FileInfo *)tlist->data; g_slist_free(ecsList); if (timerid > 0) g_source_remove(timerid); pthread_mutex_destroy(&mutex); } /** * 初始化主题库底层数据. */ void CoreThread::InitThemeSublayerData() { GtkIconTheme *theme; GtkIconFactory *factory; GtkIconSet *set; GdkPixbuf *pixbuf; theme = gtk_icon_theme_get_default(); gtk_icon_theme_append_search_path(theme, __PIXMAPS_PATH); gtk_icon_theme_append_search_path(theme, __PIXMAPS_PATH "/icon"); gtk_icon_theme_append_search_path(theme, __PIXMAPS_PATH "/menu"); gtk_icon_theme_append_search_path(theme, __PIXMAPS_PATH "/tip"); factory = gtk_icon_factory_new(); gtk_icon_factory_add_default(factory); if ((pixbuf = gtk_icon_theme_load_icon(theme, "iptux", 64, GtkIconLookupFlags(0), NULL))) { set = gtk_icon_set_new_from_pixbuf(pixbuf); gtk_icon_factory_add(factory, "iptux-logo-show", set); g_object_unref(pixbuf); } if ((pixbuf = gtk_icon_theme_load_icon(theme, "iptux-i", 64, GtkIconLookupFlags(0), NULL))) { set = gtk_icon_set_new_from_pixbuf(pixbuf); gtk_icon_factory_add(factory, "iptux-logo-hide", set); g_object_unref(pixbuf); } g_object_unref(factory); } /** * 读取共享文件数据. */ void CoreThread::ReadSharedData() { FileInfo *file; struct stat st; /* 读取共享文件数据 */ vector sharedFileList = config.GetStringList(CONFIG_SHARED_FILE_LIST); passwd = g_strdup(config.GetString(CONFIG_ACCESS_SHARED_LIMIT).c_str()); /* 分析数据并加入文件链表 */ for (size_t i = 0; i < sharedFileList.size(); ++i) { if (stat(sharedFileList[i].c_str(), &st) == -1 || !(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode))) { continue; } /* 加入文件信息到链表 */ file = new FileInfo; pblist = g_slist_append(pblist, file); file->fileid = pbn++; /* file->packetn = 0;//没必要设置此字段 */ file->fileattr = S_ISREG(st.st_mode) ? IPMSG_FILE_REGULAR : IPMSG_FILE_DIR; /* file->filesize = 0;//我可不愿意程序启动时在这儿卡住 */ /* file->fileown = NULL;//没必要设置此字段 */ file->filepath = strdup(sharedFileList[i].c_str()); } } /** * 插入消息头到TextBuffer(非UI线程安全). * @param buffer text-buffer * @param para 消息参数 */ void CoreThread::InsertHeaderToBuffer(GtkTextBuffer *buffer, MsgPara *para) { GtkTextIter iter; gchar *header; /** * @note (para->pal)可能为null. */ switch (para->stype) { case MESSAGE_SOURCE_TYPE_PAL: header = getformattime(FALSE, "%s", para->pal ? para->pal->name : _("unknown")); gtk_text_buffer_get_end_iter(buffer, &iter); gtk_text_buffer_insert_with_tags_by_name(buffer, &iter, header, -1, "pal-color", NULL); g_free(header); break; case MESSAGE_SOURCE_TYPE_SELF: header = getformattime(FALSE, "%s", g_progdt->nickname.c_str()); gtk_text_buffer_get_end_iter(buffer, &iter); gtk_text_buffer_insert_with_tags_by_name(buffer, &iter, header, -1, "me-color", NULL); g_free(header); break; case MESSAGE_SOURCE_TYPE_ERROR: header = getformattime(FALSE, "%s", _("")); gtk_text_buffer_get_end_iter(buffer, &iter); gtk_text_buffer_insert_with_tags_by_name(buffer, &iter, header, -1, "error-color", NULL); g_free(header); break; default: break; } } /** * 插入字符串到TextBuffer(非UI线程安全). * @param buffer text-buffer * @param string 字符串 */ void CoreThread::InsertStringToBuffer(GtkTextBuffer *buffer, gchar *string) { static uint32_t count = 0; GtkTextIter iter; GtkTextTag *tag; GMatchInfo *matchinfo; gchar *substring; char name[9]; // 8 +1 =9 gint startp, endp; gint urlendp; urlendp = 0; matchinfo = NULL; gtk_text_buffer_get_end_iter(buffer, &iter); g_regex_match_full(g_progdt->urlregex, string, -1, 0, GRegexMatchFlags(0), &matchinfo, NULL); while (g_match_info_matches(matchinfo)) { snprintf(name, 9, "%" PRIx32, count++); tag = gtk_text_buffer_create_tag(buffer, name, NULL); substring = g_match_info_fetch(matchinfo, 0); g_object_set_data_full(G_OBJECT(tag), "url", substring, GDestroyNotify(g_free)); g_match_info_fetch_pos(matchinfo, 0, &startp, &endp); gtk_text_buffer_insert(buffer, &iter, string + urlendp, startp - urlendp); gtk_text_buffer_insert_with_tags_by_name( buffer, &iter, string + startp, endp - startp, "url-link", name, NULL); urlendp = endp; g_match_info_next(matchinfo, NULL); } g_match_info_free(matchinfo); gtk_text_buffer_insert(buffer, &iter, string + urlendp, -1); } /** * 插入图片到TextBuffer(非UI线程安全). * @param buffer text-buffer * @param path 图片路径 */ void CoreThread::InsertPixbufToBuffer(GtkTextBuffer *buffer, gchar *path) { GtkTextIter start, end; GdkPixbuf *pixbuf; if ((pixbuf = gdk_pixbuf_new_from_file(path, NULL))) { gtk_text_buffer_get_start_iter(buffer, &start); if (gtk_text_iter_get_char(&start) == OCCUPY_OBJECT || gtk_text_iter_forward_find_char( &start, GtkTextCharPredicate(giter_compare_foreach), GUINT_TO_POINTER(OCCUPY_OBJECT), NULL)) { end = start; gtk_text_iter_forward_char(&end); gtk_text_buffer_delete(buffer, &start, &end); } gtk_text_buffer_insert_pixbuf(buffer, &start, pixbuf); g_object_unref(pixbuf); } } /** * 获取(pal)在分组模式下当前所在的群组. * @param pal class PalInfo * @return 群组信息 */ GroupInfo *CoreThread::GetPalPrevGroupItem(PalInfo *pal) { GSList *tlist; tlist = grplist; while (tlist) { if (g_slist_find(((GroupInfo *)tlist->data)->member, pal)) break; tlist = g_slist_next(tlist); } return (GroupInfo *)(tlist ? tlist->data : NULL); } /** * 增加新项到常规模式群组链表(非UI线程安全). * @param pal class PalInfo * @return 新加入的群组 */ GroupInfo *CoreThread::AttachPalRegularItem(PalInfo *pal) { GroupInfo *grpinf; grpinf = new GroupInfo; grpinf->grpid = pal->ipv4; grpinf->type = GROUP_BELONG_TYPE_REGULAR; grpinf->name = g_strdup(pal->name); grpinf->member = NULL; grpinf->buffer = gtk_text_buffer_new(g_progdt->table); grpinf->dialog = NULL; rgllist = g_slist_append(rgllist, grpinf); return grpinf; } /** * 增加新项到网段模式群组链表(非UI线程安全). * @param pal class PalInfo * @return 新加入的群组 */ GroupInfo *CoreThread::AttachPalSegmentItem(PalInfo *pal) { GroupInfo *grpinf; char *name; /* 获取局域网网段名称 */ name = ipv4_get_lan_name(pal->ipv4); name = name ? name : g_strdup(_("Others")); grpinf = new GroupInfo; grpinf->grpid = g_quark_from_static_string(name); grpinf->type = GROUP_BELONG_TYPE_SEGMENT; grpinf->name = name; grpinf->member = NULL; grpinf->buffer = gtk_text_buffer_new(g_progdt->table); grpinf->dialog = NULL; sgmlist = g_slist_append(sgmlist, grpinf); return grpinf; } /** * 增加新项到分组模式群组链表(非UI线程安全). * @param pal class PalInfo * @return 新加入的群组 */ GroupInfo *CoreThread::AttachPalGroupItem(PalInfo *pal) { GroupInfo *grpinf; char *name; /* 备份组名称,用于计算ID号 */ NO_OPERATION_C name = g_strdup(pal->group ? pal->group : _("Others")); grpinf = new GroupInfo; grpinf->grpid = g_quark_from_static_string(name); grpinf->type = GROUP_BELONG_TYPE_GROUP; grpinf->name = name; grpinf->member = NULL; grpinf->buffer = gtk_text_buffer_new(g_progdt->table); grpinf->dialog = NULL; grplist = g_slist_append(grplist, grpinf); return grpinf; } /** * 增加新项到广播模式群组链表(非UI线程安全). * @param pal class PalInfo * @return 新加入的群组 */ GroupInfo *CoreThread::AttachPalBroadcastItem(PalInfo *pal) { GroupInfo *grpinf; char *name; name = g_strdup(_("Broadcast")); grpinf = new GroupInfo; grpinf->grpid = g_quark_from_static_string(name); grpinf->type = GROUP_BELONG_TYPE_BROADCAST; grpinf->name = name; grpinf->member = NULL; grpinf->buffer = gtk_text_buffer_new(g_progdt->table); grpinf->dialog = NULL; brdlist = g_slist_append(brdlist, grpinf); return grpinf; } /** * 从群组中移除指定的好友(非UI线程安全). * @param grpinf class GroupInfo * @param pal class PalInfo */ void CoreThread::DelPalFromGroupInfoItem(GroupInfo *grpinf, PalInfo *pal) { GSList *tlist; SessionAbstract *session; if ((tlist = g_slist_find(grpinf->member, pal))) { grpinf->member = g_slist_delete_link(grpinf->member, tlist); if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->DelPalData(pal); } } } /** * 添加好友到指定的群组(非UI线程安全). * @param grpinf class GroupInfo * @param pal class PalInfo */ void CoreThread::AttachPalToGroupInfoItem(GroupInfo *grpinf, PalInfo *pal) { SessionAbstract *session; grpinf->member = g_slist_append(grpinf->member, pal); if (grpinf->dialog) { session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); session->InsertPalData(pal); } } /** * 监听UDP服务端口. * @param pcthrd 核心类 */ void CoreThread::RecvUdpData(CoreThread *self) { struct sockaddr_in addr; socklen_t len; char buf[MAX_UDPLEN]; ssize_t size; while (self->server) { len = sizeof(addr); if ((size = recvfrom(self->udpsock, buf, MAX_UDPLEN, 0, (struct sockaddr *)&addr, &len)) == -1) continue; if (size != MAX_UDPLEN) buf[size] = '\0'; UdpData::UdpDataEntry(self->config, addr.sin_addr.s_addr, buf, size); } } /** * 监听TCP服务端口. * @param pcthrd 核心类 */ void CoreThread::RecvTcpData(CoreThread *pcthrd) { pthread_t pid; int subsock; listen(pcthrd->tcpsock, 5); while (pcthrd->server) { if ((subsock = accept(pcthrd->tcpsock, NULL, NULL)) == -1) continue; pthread_create(&pid, NULL, ThreadFunc(TcpData::TcpDataEntry), GINT_TO_POINTER(subsock)); pthread_detach(pid); } } /** * 扫描处理程序内部任务(非UI线程安全). * @param pcthrd 核心类 * @return GLib库所需 */ gboolean CoreThread::WatchCoreStatus(CoreThread *pcthrd) { GList *tlist; /* 让等待队列中的群组信息项闪烁 */ pthread_mutex_lock(&pcthrd->mutex); tlist = pcthrd->msgline.head; while (tlist) { g_mwin->MakeItemBlinking((GroupInfo *)tlist->data, true); tlist = g_list_next(tlist); } pthread_mutex_unlock(&pcthrd->mutex); return TRUE; } /** * 获取特定好友发过来的文件(非UI线程安全). * @param pal class PalInfo * @return palecslist 该好友发过来待接收的文件列表 */ GSList *CoreThread::GetPalEnclosure(PalInfo *pal) { GSList *tlist, *palecslist; palecslist = NULL; for (tlist = ecsList; tlist; tlist = g_slist_next(tlist)) { if (((FileInfo *)tlist->data)->fileown == pal) { palecslist = g_slist_append(palecslist, tlist->data); } } return palecslist; } /** * 压入项进接收文件列表(非UI线程安全). * @param file 文件类指针 */ void CoreThread::PushItemToEnclosureList(FileInfo *file) { ecsList = g_slist_append(ecsList, file); } /** * 从接收文件列表删除项(非UI线程安全). * @param file 文件类指针 */ void CoreThread::PopItemFromEnclosureList(FileInfo *file) { ecsList = g_slist_remove(ecsList, file); delete file; } void CoreThread::Lock() { pthread_mutex_lock(&mutex); } void CoreThread::Unlock() { pthread_mutex_unlock(&mutex); } } // namespace iptux iptux-0.7.4/src/iptux/CoreThread.h000066400000000000000000000117241323207530100170250ustar00rootroot00000000000000// // C++ Interface: CoreThread // // Description: // 程序中的核心线程类,实际上也被设计成了所有底层核心数据的中心点, // 所有数据的更新、查询、插入、删除都必须通过本类接口才能完成。 // ----------------------------------------------------- // 2012.02:把文件传送的核心数据全部放在CoreThread类。 // prlist不变,增加ecsList来存放好友发来文件. //------------------------------------------------------ // Author: cwll , (C) 2012 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_CORETHREAD_H #define IPTUX_CORETHREAD_H #include "iptux/IptuxConfig.h" #include "iptux/mess.h" namespace iptux { /** * @note 请保证插入或更新某成员时,底层优先于UI;删除某成员时,UI优先于底层, * 否则你会把所有事情都搞砸. \n * @note 鉴于(GroupInfo::member)成员发生变动时必须保证函数处于UI线程安全的环境, * 所以UI线程安全的函数对(GroupInfo::member)的访问无须加锁.\n * 若此特性不可被如此利用,请报告bug. \n * @note 如果本程序编码中的某处没有遵循以上规则,请报告bug. */ class CoreThread { public: CoreThread(IptuxConfig &config); ~CoreThread(); void CoreThreadEntry(); void WriteSharedData(); GSList *GetPalList(); void Lock(); void Unlock(); void InsertMessage(MsgPara *para); void InsertMsgToGroupInfoItem(GroupInfo *grpinf, MsgPara *para); static void SendNotifyToAll(CoreThread *pcthrd); static void SendFeatureData(PalInfo *pal); static void SendBroadcastExit(PalInfo *pal); static void UpdateMyInfo(); void ClearAllPalFromList(); PalInfo *GetPalFromList(in_addr_t ipv4); bool ListContainPal(in_addr_t ipv4); void DelPalFromList(in_addr_t ipv4); void UpdatePalToList(in_addr_t ipv4); void AttachPalToList(PalInfo *pal); GroupInfo *GetPalRegularItem(PalInfo *pal); GroupInfo *GetPalSegmentItem(PalInfo *pal); GroupInfo *GetPalGroupItem(PalInfo *pal); GroupInfo *GetPalBroadcastItem(PalInfo *pal); bool BlacklistContainItem(in_addr_t ipv4); void AttachItemToBlacklist(in_addr_t ipv4); void ClearBlacklist(); guint GetMsglineItems(); GroupInfo *GetMsglineHeadItem(); bool MsglineContainItem(GroupInfo *grpinf); void PushItemToMsgline(GroupInfo *grpinf); void PopItemFromMsgline(GroupInfo *grpinf); GSList *GetPalEnclosure(PalInfo *pal); void PushItemToEnclosureList(FileInfo *file); void PopItemFromEnclosureList(FileInfo *file); GSList *GetPalRcvdEnclosure(PalInfo *pal); void AttachFileToPublic(FileInfo *file); void DelFileFromPublic(uint32_t fileid); void ClearFileFromPublic(); GSList *GetPublicFileList(); void AttachFileToPrivate(FileInfo *file); void DelFileFromPrivate(uint32_t fileid); void ClearFileFromPrivate(); FileInfo *GetFileFromAll(uint32_t fileid); FileInfo *GetFileFromAllWithPacketN(uint32_t packageNum, uint32_t filectime); const char *GetAccessPublicLimit(); void SetAccessPublicLimit(const char *limit); private: IptuxConfig &config; void InitSublayer(); void ClearSublayer(); void InitThemeSublayerData(); void ReadSharedData(); void InsertHeaderToBuffer(GtkTextBuffer *buffer, MsgPara *para); void InsertStringToBuffer(GtkTextBuffer *buffer, gchar *string); void InsertPixbufToBuffer(GtkTextBuffer *buffer, gchar *path); GroupInfo *GetPalPrevGroupItem(PalInfo *pal); GroupInfo *AttachPalRegularItem(PalInfo *pal); GroupInfo *AttachPalSegmentItem(PalInfo *pal); GroupInfo *AttachPalGroupItem(PalInfo *pal); GroupInfo *AttachPalBroadcastItem(PalInfo *pal); void DelPalFromGroupInfoItem(GroupInfo *grpinf, PalInfo *pal); void AttachPalToGroupInfoItem(GroupInfo *grpinf, PalInfo *pal); int tcpsock, udpsock; //程序的服务监听套接口 bool server; //程序是否正在服务 GSList *pallist; //好友链表(成员不能被删除) GSList *rgllist, *sgmlist, *grplist, *brdlist; //群组链表(成员不能被删除) GSList *blacklist; //黑名单链表 GQueue msgline; //消息队列 uint32_t pbn, prn; //当前已使用的文件编号(共享/私有) GSList *pblist, *prlist; //文件链表(共享/私有) GSList *ecsList; //文件链表(好友发过来) // GSList *rcvdList; //文件链表(好友发过来已接收) std::string passwd; //共享文件密码 guint timerid; //定时器ID pthread_mutex_t mutex; //锁 //回调处理部分函数 private: static void RecvUdpData(CoreThread *pcthrd); static void RecvTcpData(CoreThread *pcthrd); static gboolean WatchCoreStatus(CoreThread *pcthrd); //内联成员函数 public: inline int &TcpSockQuote() { return tcpsock; } inline int &UdpSockQuote() { return udpsock; } inline uint32_t &PbnQuote() { return pbn; } inline uint32_t &PrnQuote() { return prn; } }; } // namespace iptux #endif iptux-0.7.4/src/iptux/DataSettings.cpp000066400000000000000000001615571323207530100177440ustar00rootroot00000000000000// // C++ Implementation: DataSettings // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "DataSettings.h" #include "iptux/CoreThread.h" #include "iptux/ProgramData.h" #include "iptux/SoundSystem.h" #include "iptux/callback.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/ipmsg.h" #include "iptux/output.h" #include "iptux/support.h" #include "iptux/utils.h" using namespace std; namespace iptux { /** * 类构造函数. */ DataSettings::DataSettings() : widset(NULL), mdlset(NULL) { InitSublayer(); } /** * 类析构函数. */ DataSettings::~DataSettings() { ClearSublayer(); } /** * 程序数据设置入口. * @param parent 父窗口指针 */ void DataSettings::ResetDataEntry(GtkWidget *parent) { DataSettings dset; GtkWidget *dialog; GtkWidget *note, *label; dialog = dset.CreateMainDialog(parent); /* 创建相关数据设置标签 */ note = gtk_notebook_new(); gtk_notebook_set_tab_pos(GTK_NOTEBOOK(note), GTK_POS_LEFT); gtk_notebook_set_scrollable(GTK_NOTEBOOK(note), TRUE); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), note, TRUE, TRUE, 0); label = gtk_label_new(_("Personal")); gtk_notebook_append_page(GTK_NOTEBOOK(note), dset.CreatePersonal(), label); label = gtk_label_new(_("System")); gtk_notebook_append_page(GTK_NOTEBOOK(note), dset.CreateSystem(), label); #ifdef HAVE_GST label = gtk_label_new(_("Sound")); gtk_notebook_append_page(GTK_NOTEBOOK(note), dset.CreateSound(), label); #endif label = gtk_label_new(_("Network")); gtk_notebook_append_page(GTK_NOTEBOOK(note), dset.CreateNetwork(), label); /* 设置相关数据默认值 */ dset.SetPersonalValue(); dset.SetSystemValue(); #ifdef HAVE_GST dset.SetSoundValue(); #endif dset.SetNetworkValue(); /* 运行对话框 */ gtk_widget_show_all(dialog); mark: switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_OK: dset.ObtainPersonalValue(); dset.ObtainSystemValue(); #ifdef HAVE_GST dset.ObtainSoundValue(); #endif dset.ObtainNetworkValue(); g_progdt->WriteProgData(); CoreThread::UpdateMyInfo(); break; case GTK_RESPONSE_APPLY: dset.ObtainPersonalValue(); dset.ObtainSystemValue(); #ifdef HAVE_GST dset.ObtainSoundValue(); #endif dset.ObtainNetworkValue(); g_progdt->WriteProgData(); CoreThread::UpdateMyInfo(); goto mark; default: break; } gtk_widget_destroy(dialog); } /** * 初始化底层数据. */ void DataSettings::InitSublayer() { GtkTreeModel *model; g_datalist_init(&widset); g_datalist_init(&mdlset); model = CreateIconModel(); g_datalist_set_data_full(&mdlset, "icon-model", model, GDestroyNotify(g_object_unref)); FillIconModel(model); #ifdef HAVE_GST model = CreateSndModel(); g_datalist_set_data_full(&mdlset, "sound-model", model, GDestroyNotify(g_object_unref)); FillSndModel(model); #endif model = CreateNetworkModel(); g_datalist_set_data_full(&mdlset, "network-model", model, GDestroyNotify(g_object_unref)); FillNetworkModel(model); } /** * 清空底层数据. */ void DataSettings::ClearSublayer() { g_datalist_clear(&widset); g_datalist_clear(&mdlset); } /** * 创建主对话框. * @param parent 父窗口指针 * @return 对话框 */ GtkWidget *DataSettings::CreateMainDialog(GtkWidget *parent) { GtkWidget *dialog; dialog = gtk_dialog_new_with_buttons( _("Preferences"), GTK_WINDOW(parent), GtkDialogFlags(GTK_DIALOG_MODAL), GTK_STOCK_OK, GTK_RESPONSE_OK, GTK_STOCK_APPLY, GTK_RESPONSE_APPLY, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); gtk_container_set_border_width(GTK_CONTAINER(dialog), 5); gtk_widget_set_size_request(dialog, 520, -1); g_datalist_set_data(&widset, "dialog-widget", dialog); return dialog; } /** * 创建与个人相关的数据设置窗体. * @return 主窗体 */ GtkWidget *DataSettings::CreatePersonal() { GtkWidget *box, *hbox; GtkWidget *frame, *sw; GtkWidget *label, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); /* 昵称 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Your nickname:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Please input your nickname!")); g_datalist_set_data(&widset, "nickname-entry-widget", widget); /* 群组 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Your group name:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Please input your group name!")); g_datalist_set_data(&widset, "mygroup-entry-widget", widget); /* 头像 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Your face picture:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "icon-model")); widget = CreateIconTree(model); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_datalist_set_data(&widset, "myicon-combo-widget", widget); button = gtk_button_new_with_label("..."); g_object_set_data(G_OBJECT(button), "icon-combo-widget", widget); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect(button, "clicked", G_CALLBACK(AddNewIcon), &widset); /* 文件存档 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Save files to: ")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = CreateArchiveChooser(); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_datalist_set_data(&widset, "archive-chooser-widget", widget); hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 5); /* 个人形象照片 */ NO_OPERATION_C frame = gtk_frame_new(_("Photo")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(hbox), frame, FALSE, FALSE, 0); button = gtk_button_new(); gtk_widget_set_size_request(button, MAX_PREVIEWSIZE, MAX_PREVIEWSIZE); gtk_container_add(GTK_CONTAINER(frame), button); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ChoosePhoto), &widset); widget = gtk_image_new(); gtk_container_add(GTK_CONTAINER(button), widget); g_datalist_set_data(&widset, "photo-image-widget", widget); /* 个性签名 */ NO_OPERATION_C frame = gtk_frame_new(_("Signature")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_end(GTK_BOX(hbox), frame, TRUE, TRUE, 0); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_container_add(GTK_CONTAINER(frame), sw); widget = gtk_text_view_new(); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(widget), GTK_WRAP_WORD_CHAR); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "sign-textview-widget", widget); return box; } /** * 创建与系统相关的数据设置窗体. * @return 主窗体 */ GtkWidget *DataSettings::CreateSystem() { GtkWidget *box, *hbox; GtkWidget *label, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); /* 候选编码 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Candidate network coding:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Candidate network coding")); g_datalist_set_data(&widset, "codeset-entry-widget", widget); /* 首选编码 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Preference network coding:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Preference network coding (You should be aware of " "what you are doing if you want to modify it.)")); g_datalist_set_data(&widset, "encode-entry-widget", widget); /* 好友头像 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Pal's default face picture:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "icon-model")); widget = CreateIconTree(model); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_datalist_set_data(&widset, "palicon-combo-widget", widget); button = gtk_button_new_with_label("..."); g_object_set_data(G_OBJECT(button), "icon-combo-widget", widget); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect(button, "clicked", G_CALLBACK(AddNewIcon), &widset); /* 面板字体 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Panel font:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = CreateFontChooser(); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_datalist_set_data(&widset, "font-chooser-widget", widget); /* 有消息时直接弹出聊天窗口 */ widget = gtk_check_button_new_with_label(_("Automatically open the chat dialog")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "chat-check-widget", widget); /* 隐藏面板,只显示状态图标 */ widget = gtk_check_button_new_with_label( _("Automatically hide the panel after login")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "statusicon-check-widget", widget); /* 打开文件传输管理器 */ widget = gtk_check_button_new_with_label( _("Automatically open the File Transmission Management")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "transmission-check-widget", widget); /* enter键发送消息 */ widget = gtk_check_button_new_with_label(_("Use the 'Enter' key to send message")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "enterkey-check-widget", widget); /* 清空聊天历史记录 */ widget = gtk_check_button_new_with_label( _("Automatically clean up the chat history")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "history-check-widget", widget); /* 记录日志 */ widget = gtk_check_button_new_with_label(_("Save the chat history")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "log-check-widget", widget); /* 黑名单 */ widget = gtk_check_button_new_with_label(_("Use the Blacklist (NOT recommended)")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "blacklist-check-widget", widget); /* 过滤共享文件请求 */ widget = gtk_check_button_new_with_label(_("Filter the request of sharing files")); gtk_box_pack_start(GTK_BOX(box), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "shared-check-widget", widget); return box; } /** * 创建与声音相关的数据设置窗体. * @return 主窗体 */ GtkWidget *DataSettings::CreateSound() { GtkWidget *box, *hbox, *vbox; GtkWidget *frame, *sw, *chkbutton; GtkWidget *label, *button, *widget; GtkTreeSelection *selection; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); /* 声音支持 */ NO_OPERATION_C chkbutton = gtk_check_button_new_with_label(_("Activate the sound support")); gtk_box_pack_start(GTK_BOX(box), chkbutton, FALSE, FALSE, 3); g_datalist_set_data(&widset, "sound-check-widget", chkbutton); /* 音量调整 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); g_signal_connect(chkbutton, "toggled", G_CALLBACK(AdjustSensitive), hbox); label = gtk_label_new(_("Volume Control: ")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_hscale_new_with_range(0.0, 1.0, 0.01); gtk_scale_set_draw_value(GTK_SCALE(widget), FALSE); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "value-changed", G_CALLBACK(AdjustVolume), NULL); g_datalist_set_data(&widset, "volume-hscale-widget", widget); /* 声音事件 */ NO_OPERATION_C frame = gtk_frame_new(_("Sound Event")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(box), frame, TRUE, TRUE, 3); g_signal_connect(chkbutton, "toggled", G_CALLBACK(AdjustSensitive), frame); vbox = gtk_vbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(frame), vbox); /*/* 声音事件树 */ sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(vbox), sw, TRUE, TRUE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "sound-model")); widget = CreateSndTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_signal_connect(widget, "button-press-event", G_CALLBACK(PopupPickMenu), NULL); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); g_signal_connect(selection, "changed", G_CALLBACK(SndtreeSelectItemChanged), &widset); g_datalist_set_data(&widset, "sound-treeview-widget", widget); /*/* 声音测试 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0); widget = CreateSndChooser(); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 5); g_signal_connect(widget, "file-set", G_CALLBACK(ChooserResetSndtree), &widset); g_datalist_set_data(&widset, "sound-chooser-widget", widget); button = gtk_button_new_with_label(_("Test")); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(PlayTesting), &widset); button = gtk_button_new_with_label(_("Stop")); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect(button, "clicked", G_CALLBACK(StopTesting), NULL); return box; } /** * 创建与网络相关的数据设置窗体. * @return 主窗体 */ GtkWidget *DataSettings::CreateNetwork() { char buf[MAX_BUFLEN]; GtkWidget *box, *hbox, *vbox; GtkWidget *frame, *sw; GtkWidget *label, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); /* 接受输入 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("From:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Beginning of the IP(v4) section")); g_signal_connect(widget, "insert-text", G_CALLBACK(entry_insert_numeric), NULL); g_datalist_set_data(&widset, "startip-entry-widget", widget); label = gtk_label_new(_("To:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("End of the IP(v4) section")); g_signal_connect(widget, "insert-text", G_CALLBACK(entry_insert_numeric), NULL); g_datalist_set_data(&widset, "endip-entry-widget", widget); /* 增加&删除按钮 */ hbox = gtk_hbutton_box_new(); gtk_button_box_set_layout(GTK_BUTTON_BOX(hbox), GTK_BUTTONBOX_SPREAD); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); snprintf(buf, MAX_BUFLEN, "%s↓↓", _("Add")); button = gtk_button_new_with_label(buf); gtk_box_pack_end(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ClickAddIpseg), &widset); snprintf(buf, MAX_BUFLEN, "%s↑↑", _("Delete")); button = gtk_button_new_with_label(buf); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ClickDelIpseg), &widset); /* 网段树&实用性按钮 */ NO_OPERATION_C frame = gtk_frame_new(_("Added IP(v4) Section:")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(box), frame, TRUE, TRUE, 5); hbox = gtk_hbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(frame), hbox); /*/* 网段树 */ sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(hbox), sw, TRUE, TRUE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "network-model")); widget = CreateNetworkTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "network-treeview-widget", widget); /*/* 实用性按钮 */ vbox = gtk_vbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(hbox), vbox, FALSE, FALSE, 0); button = gtk_button_new_with_label(_("Import")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ImportNetSegment), this); button = gtk_button_new_with_label(_("Export")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ExportNetSegment), this); button = gtk_button_new_with_label(_("Clear")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ClearNetSegment), &mdlset); return box; } /** * 为界面设置与个人相关的数据 */ void DataSettings::SetPersonalValue() { char path[MAX_PATHLEN]; GtkWidget *widget; GtkTreeModel *model; GtkTextBuffer *buffer; GdkPixbuf *pixbuf; gint active; widget = GTK_WIDGET(g_datalist_get_data(&widset, "nickname-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), g_progdt->nickname.c_str()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "mygroup-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), g_progdt->mygroup.c_str()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "myicon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = IconfileGetItemPos(model, g_progdt->myicon.c_str()); gtk_combo_box_set_active(GTK_COMBO_BOX(widget), active); widget = GTK_WIDGET(g_datalist_get_data(&widset, "archive-chooser-widget")); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(widget), g_progdt->path.c_str()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "photo-image-widget")); snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH "/photo", g_get_user_config_dir()); if ((pixbuf = gdk_pixbuf_new_from_file_at_size(path, MAX_PREVIEWSIZE, MAX_PREVIEWSIZE, NULL))) { gtk_image_set_from_pixbuf(GTK_IMAGE(widget), pixbuf); g_object_unref(pixbuf); } widget = GTK_WIDGET(g_datalist_get_data(&widset, "sign-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); gtk_text_buffer_set_text(buffer, g_progdt->sign.c_str(), -1); } /** * 为界面设置与系统相关的数据 */ void DataSettings::SetSystemValue() { GtkWidget *widget; GtkTreeModel *model; gint active; widget = GTK_WIDGET(g_datalist_get_data(&widset, "codeset-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), g_progdt->codeset.c_str()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "encode-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), g_progdt->encode.c_str()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "palicon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = IconfileGetItemPos(model, g_progdt->palicon); gtk_combo_box_set_active(GTK_COMBO_BOX(widget), active); widget = GTK_WIDGET(g_datalist_get_data(&widset, "font-chooser-widget")); gtk_font_button_set_font_name(GTK_FONT_BUTTON(widget), g_progdt->font); widget = GTK_WIDGET(g_datalist_get_data(&widset, "chat-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsAutoOpenCharDialog()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "statusicon-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsAutoHidePanelAfterLogin()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "transmission-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsAutoOpenFileTrans()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "enterkey-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsEnterSendMessage()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "history-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsAutoCleanChatHistory()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "log-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsSaveChatHistory()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "blacklist-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsUsingBlacklist()); widget = GTK_WIDGET(g_datalist_get_data(&widset, "shared-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), g_progdt->IsFilterFileShareRequest()); } /** * 为界面设置与声音相关的数据 */ void DataSettings::SetSoundValue() { GtkWidget *widget; GtkTreeSelection *selection; GtkTreeModel *model; GtkTreeIter iter; gchar *filepath; widget = GTK_WIDGET(g_datalist_get_data(&widset, "sound-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), FLAG_ISSET(g_progdt->sndfgs, 0)); gtk_toggle_button_toggled(GTK_TOGGLE_BUTTON(widget)); widget = GTK_WIDGET(g_datalist_get_data(&widset, "volume-hscale-widget")); gtk_range_set_value(GTK_RANGE(widget), g_progdt->volume); widget = GTK_WIDGET(g_datalist_get_data(&widset, "sound-treeview-widget")); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); if (gtk_tree_selection_get_selected(selection, &model, &iter)) { widget = GTK_WIDGET(g_datalist_get_data(&widset, "sound-chooser-widget")); gtk_tree_model_get(model, &iter, 2, &filepath, -1); gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(widget), filepath); g_free(filepath); } } /** * 为界面设置与网络相关的数据 */ void DataSettings::SetNetworkValue() {} /** * 头像树(icon-tree)底层数据结构. * 2,0 icon,1 iconfile \n * 头像;文件名(带后缀) \n * @return icon-model */ GtkTreeModel *DataSettings::CreateIconModel() { GtkListStore *model; model = gtk_list_store_new(2, GDK_TYPE_PIXBUF, G_TYPE_STRING); return GTK_TREE_MODEL(model); } /** * 声音树(sound-tree)底层数据结构. * 3,0 toggled,1 comment,2 path \n * 是否被选中;用途注释;文件路径 \n * @return sound-model */ GtkTreeModel *DataSettings::CreateSndModel() { GtkListStore *model; model = gtk_list_store_new(3, G_TYPE_BOOLEAN, G_TYPE_STRING, G_TYPE_STRING); return GTK_TREE_MODEL(model); } /** * 网络树(network-tree)底层数据结构. * 3,0 startip,1 endip,2 description \n * 起始IP;终止IP;描述 \n * @return network-model */ GtkTreeModel *DataSettings::CreateNetworkModel() { GtkListStore *model; model = gtk_list_store_new(3, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING); gtk_tree_sortable_set_default_sort_func( GTK_TREE_SORTABLE(model), GtkTreeIterCompareFunc(NetworkTreeCompareFunc), NULL, NULL); gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); return GTK_TREE_MODEL(model); } /** * 为头像树(icon-tree)填充底层数据. * @param model icon-model */ void DataSettings::FillIconModel(GtkTreeModel *model) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkTreeIter iter; struct dirent *dirt; DIR *dir; char *file; theme = gtk_icon_theme_get_default(); if ((dir = opendir(__PIXMAPS_PATH "/icon"))) { while ((dirt = readdir(dir))) { if (strcmp(dirt->d_name, ".") == 0 || strcmp(dirt->d_name, "..") == 0) continue; file = iptux_erase_filename_suffix(dirt->d_name); if ((pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, dirt->d_name, -1); g_object_unref(pixbuf); } g_free(file); } closedir(dir); } } /** * 为声音树(sound-tree)填充底层数据. * @param model sound-model */ void DataSettings::FillSndModel(GtkTreeModel *model) { GtkTreeIter iter; gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, FLAG_ISSET(g_progdt->sndfgs, 2), 1, _("Transfer finished"), 2, g_progdt->transtip, -1); gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, FLAG_ISSET(g_progdt->sndfgs, 1), 1, _("Message received"), 2, g_progdt->msgtip, -1); } /** * 为网络树(network-tree)填充底层数据. * @param model network-model * @note 与修改此链表的代码段是串行关系,无需加锁 */ void DataSettings::FillNetworkModel(GtkTreeModel *model) { GtkTreeIter iter; GSList *tlist; NetSegment *pns; tlist = g_progdt->netseg; while (tlist) { pns = (NetSegment *)tlist->data; gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pns->startip, 1, pns->endip, 2, pns->description, -1); tlist = g_slist_next(tlist); } } /** * 创建头像树(icon-tree). * @param model icon-model * @return 头像树 */ GtkWidget *DataSettings::CreateIconTree(GtkTreeModel *model) { GtkWidget *combo; GtkCellRenderer *cell; combo = gtk_combo_box_new_with_model(model); gtk_combo_box_set_wrap_width(GTK_COMBO_BOX(combo), 5); cell = gtk_cell_renderer_pixbuf_new(); gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(combo), cell, FALSE); gtk_cell_layout_set_attributes(GTK_CELL_LAYOUT(combo), cell, "pixbuf", 0, NULL); return combo; } /** * 创建声音树(sound-tree). * @param model sound-model * @return 声音树 */ GtkWidget *DataSettings::CreateSndTree(GtkTreeModel *model) { GtkWidget *view; GtkCellRenderer *cell; GtkTreeViewColumn *column; GtkTreeSelection *selection; GtkTreePath *path; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); cell = gtk_cell_renderer_toggle_new(); column = gtk_tree_view_column_new_with_attributes(_("Play"), cell, "active", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect_swapped(cell, "toggled", G_CALLBACK(model_turn_select), model); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Event"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); /* 函数ChooserResetView()要求必须选择一项 */ selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_BROWSE); path = gtk_tree_path_new_from_string("0"); gtk_tree_selection_select_path(selection, path); gtk_tree_path_free(path); return view; } /** * 创建网络树(network-tree). * @param model network-model * @return 网络树 */ GtkWidget *DataSettings::CreateNetworkTree(GtkTreeModel *model) { GtkWidget *view; GtkCellRenderer *cell; GtkTreeViewColumn *column; GtkTreeSelection *selection; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); gtk_tree_view_set_rubber_banding(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("From"), cell, "text", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("To"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); g_object_set(cell, "editable", TRUE, NULL); g_object_set_data(G_OBJECT(cell), "column-number", GINT_TO_POINTER(2)); column = gtk_tree_view_column_new_with_attributes(_("Description"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect(cell, "edited", G_CALLBACK(CellEditText), model); return view; } /** * 创建文件归档选择器. * @return 选择器 */ GtkWidget *DataSettings::CreateArchiveChooser() { GtkWidget *chooser; chooser = gtk_file_chooser_button_new(_("Please select download folder"), GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER); gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(chooser), FALSE); gtk_file_chooser_set_show_hidden(GTK_FILE_CHOOSER(chooser), FALSE); gtk_file_chooser_set_do_overwrite_confirmation(GTK_FILE_CHOOSER(chooser), TRUE); return chooser; } /** * 创建字体选择器. * @return 选择器 */ GtkWidget *DataSettings::CreateFontChooser() { GtkWidget *chooser; chooser = gtk_font_button_new(); gtk_font_button_set_show_style(GTK_FONT_BUTTON(chooser), TRUE); gtk_font_button_set_show_size(GTK_FONT_BUTTON(chooser), TRUE); gtk_font_button_set_use_font(GTK_FONT_BUTTON(chooser), TRUE); gtk_font_button_set_use_size(GTK_FONT_BUTTON(chooser), TRUE); gtk_font_button_set_title(GTK_FONT_BUTTON(chooser), _("Select Font")); return chooser; } /** * 创建声音文件选择器. * @return 选择器 */ GtkWidget *DataSettings::CreateSndChooser() { GtkWidget *chooser; chooser = gtk_file_chooser_button_new(_("Please select a sound file"), GTK_FILE_CHOOSER_ACTION_OPEN); gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(chooser), TRUE); gtk_file_chooser_set_show_hidden(GTK_FILE_CHOOSER(chooser), FALSE); return chooser; } /** * 获取与个人相关的数据. */ void DataSettings::ObtainPersonalValue() { GtkWidget *widget; GdkPixbuf *pixbuf; GtkTextBuffer *buffer; GtkTextIter start, end; GtkTreeModel *model; GtkTreeIter iter; char path[MAX_PATHLEN], *file; const gchar *text; gint active; widget = GTK_WIDGET(g_datalist_get_data(&widset, "nickname-entry-widget")); if (*(text = gtk_entry_get_text(GTK_ENTRY(widget))) != '\0') { g_progdt->nickname = text; } widget = GTK_WIDGET(g_datalist_get_data(&widset, "mygroup-entry-widget")); if (*(text = gtk_entry_get_text(GTK_ENTRY(widget))) != '\0') { g_progdt->mygroup = text; } else { g_progdt->mygroup = ""; } widget = GTK_WIDGET(g_datalist_get_data(&widset, "myicon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = gtk_combo_box_get_active(GTK_COMBO_BOX(widget)); if (active != -1) { snprintf(path, MAX_PATHLEN, "%d", active); gtk_tree_model_get_iter_from_string(model, &iter, path); gtk_tree_model_get(model, &iter, 1, &file, -1); if (strcmp(g_progdt->myicon.c_str(), file) != 0) { snprintf(path, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", file); if (access(path, F_OK) != 0) { g_free(file); g_progdt->myicon = "my-icon"; snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/my-icon", g_get_user_config_dir()); gtk_tree_model_get(model, &iter, 0, &pixbuf, -1); gdk_pixbuf_save(pixbuf, path, "png", NULL, NULL); gtk_icon_theme_add_builtin_icon(g_progdt->myicon.c_str(), MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } else { g_progdt->myicon = file; } } else g_free(file); } widget = GTK_WIDGET(g_datalist_get_data(&widset, "archive-chooser-widget")); g_progdt->path = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(widget)); widget = GTK_WIDGET(g_datalist_get_data(&widset, "sign-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); gtk_text_buffer_get_bounds(buffer, &start, &end); g_progdt->sign = gtk_text_buffer_get_text(buffer, &start, &end, FALSE); } /** * 获取与系统相关的数据. */ void DataSettings::ObtainSystemValue() { GtkWidget *widget; GdkPixbuf *pixbuf; GtkTreeModel *model; GtkTreeIter iter; char path[MAX_PATHLEN], *file; gchar *text; gint active; widget = GTK_WIDGET(g_datalist_get_data(&widset, "codeset-entry-widget")); text = gtk_editable_get_chars(GTK_EDITABLE(widget), 0, -1); g_strstrip(text); if (*text != '\0') { g_progdt->codeset = text; } else g_free(text); widget = GTK_WIDGET(g_datalist_get_data(&widset, "encode-entry-widget")); text = gtk_editable_get_chars(GTK_EDITABLE(widget), 0, -1); g_strstrip(text); if (*text != '\0') { g_progdt->encode = text; } else g_free(text); widget = GTK_WIDGET(g_datalist_get_data(&widset, "palicon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = gtk_combo_box_get_active(GTK_COMBO_BOX(widget)); if (active != -1) { snprintf(path, MAX_PATHLEN, "%d", active); gtk_tree_model_get_iter_from_string(model, &iter, path); gtk_tree_model_get(model, &iter, 1, &file, -1); if (strcmp(g_progdt->palicon, file) != 0) { snprintf(path, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", file); if (access(path, F_OK) != 0) { g_free(file); g_free(g_progdt->palicon); g_progdt->palicon = g_strdup("pal-icon"); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/pal-icon", g_get_user_config_dir()); gtk_tree_model_get(model, &iter, 0, &pixbuf, -1); gdk_pixbuf_save(pixbuf, path, "png", NULL, NULL); gtk_icon_theme_add_builtin_icon(g_progdt->palicon, MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } else { g_free(g_progdt->palicon); g_progdt->palicon = file; } } else g_free(file); } widget = GTK_WIDGET(g_datalist_get_data(&widset, "font-chooser-widget")); g_free(g_progdt->font); g_progdt->font = g_strdup(gtk_font_button_get_font_name(GTK_FONT_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "chat-check-widget")); g_progdt->SetFlag(7, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "statusicon-check-widget")); g_progdt->SetFlag(6, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "transmission-check-widget")); g_progdt->SetFlag(5, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "enterkey-check-widget")); g_progdt->SetFlag(4, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "history-check-widget")); g_progdt->SetFlag(3, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "log-check-widget")); g_progdt->SetFlag(2, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "blacklist-check-widget")); g_progdt->SetFlag(1, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); widget = GTK_WIDGET(g_datalist_get_data(&widset, "shared-check-widget")); g_progdt->SetFlag(0, gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))); } /** * 获取与声音相关的数据. */ void DataSettings::ObtainSoundValue() { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gboolean active; gchar *path; widget = GTK_WIDGET(g_datalist_get_data(&widset, "sound-check-widget")); if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))) FLAG_SET(g_progdt->sndfgs, 0); else FLAG_CLR(g_progdt->sndfgs, 0); widget = GTK_WIDGET(g_datalist_get_data(&widset, "volume-hscale-widget")); g_progdt->volume = gtk_range_get_value(GTK_RANGE(widget)); /** * @see ::FillSndModel(),数据的获取应该与其保持一致. */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "sound-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); /*/* 获取文件传输完成的声音信息 */ gtk_tree_model_get_iter_from_string(model, &iter, "0"); gtk_tree_model_get(model, &iter, 0, &active, 2, &path, -1); if (active) FLAG_SET(g_progdt->sndfgs, 2); else FLAG_CLR(g_progdt->sndfgs, 2); g_free(g_progdt->transtip); g_progdt->transtip = path; /*/* 获取有消息到来的声音信息 */ gtk_tree_model_get_iter_from_string(model, &iter, "1"); gtk_tree_model_get(model, &iter, 0, &active, 2, &path, -1); if (active) FLAG_SET(g_progdt->sndfgs, 1); else FLAG_CLR(g_progdt->sndfgs, 1); g_free(g_progdt->msgtip); g_progdt->msgtip = path; } /** * 获取与网络相关的数据. */ void DataSettings::ObtainNetworkValue() { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; NetSegment *ns; GSList *tlist; widget = GTK_WIDGET(g_datalist_get_data(&widset, "network-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); g_progdt->Lock(); for (tlist = g_progdt->netseg; tlist; tlist = g_slist_next(tlist)) delete (NetSegment *)tlist->data; g_slist_free(g_progdt->netseg); g_progdt->netseg = NULL; if (gtk_tree_model_get_iter_first(model, &iter)) { do { ns = new NetSegment; gtk_tree_model_get(model, &iter, 0, &ns->startip, 1, &ns->endip, 2, &ns->description, -1); g_progdt->netseg = g_slist_append(g_progdt->netseg, ns); } while (gtk_tree_model_iter_next(model, &iter)); } g_progdt->Unlock(); } /** * 写出网段数据到指定文件. * @param filename 文件名 * @param list 网段数据链表 */ void DataSettings::WriteNetSegment(const char *filename, GSList *list) { GtkWidget *parent; GSList *tlist; NetSegment *pns; FILE *stream; if (!(stream = fopen(filename, "w"))) { parent = GTK_WIDGET(g_datalist_get_data(&widset, "dialog-widget")); pop_warning(parent, _("Fopen() file \"%s\" failed!\n%s"), filename, strerror(errno)); return; } fprintf(stream, "#format (startIP - endIP //description)"); tlist = list; while (tlist) { pns = (NetSegment *)tlist->data; fprintf(stream, "\n%s - %s //%s", pns->startip, pns->endip, pns->description ? pns->description : ""); tlist = g_slist_next(tlist); } fclose(stream); } /** * 从指定文件读取网段数据. * @param filename 文件名 * @retval list 网段数据链表指针,数据由此返回 */ void DataSettings::ReadNetSegment(const char *filename, GSList **list) { GtkWidget *parent; char buf[3][MAX_BUFLEN], *lineptr; in_addr_t ipv4; NetSegment *ns; FILE *stream; size_t n; if (!(stream = fopen(filename, "r"))) { parent = GTK_WIDGET(g_datalist_get_data(&widset, "dialog-widget")); pop_warning(parent, _("Fopen() file \"%s\" failed!\n%s"), filename, strerror(errno)); return; } n = 0; lineptr = NULL; while (getline(&lineptr, &n, stream) != -1) { if (*(lineptr + strspn(lineptr, "\t\x20")) == '#') continue; switch (sscanf(lineptr, "%s - %s //%s", buf[0], buf[1], buf[2])) { case 3: if (inet_pton(AF_INET, buf[0], &ipv4) <= 0 || inet_pton(AF_INET, buf[1], &ipv4) <= 0) break; ns = new NetSegment; *list = g_slist_append(*list, ns); ns->startip = g_strdup(buf[0]); ns->endip = g_strdup(buf[1]); ns->description = g_strdup(buf[2]); break; case 2: if (inet_pton(AF_INET, buf[0], &ipv4) <= 0 || inet_pton(AF_INET, buf[1], &ipv4) <= 0) break; ns = new NetSegment; *list = g_slist_append(*list, ns); ns->startip = g_strdup(buf[0]); ns->endip = g_strdup(buf[1]); break; default: break; } } g_free(lineptr); fclose(stream); } /** * 创建选择项的弹出菜单. * @param model model * @return 菜单 */ GtkWidget *DataSettings::CreatePopupMenu(GtkTreeModel *model) { GtkWidget *menu, *menuitem; menu = gtk_menu_new(); menuitem = gtk_menu_item_new_with_label(_("Select All")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_select_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Reverse Select")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_turn_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Clear Up")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_clear_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); return menu; } /** * 查询(pathname)文件在(model)中的位置,若没有则加入到后面. * @param model model * @param pathname 文件路径 * @return 位置 */ gint DataSettings::IconfileGetItemPos(GtkTreeModel *model, const char *pathname) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkTreeIter iter; const char *ptr; gchar *file; gint result, pos; /* 让ptr指向文件名 */ ptr = strrchr(pathname, '/'); ptr = ptr ? ptr + 1 : pathname; /* 查询model中是否已经存在此文件 */ pos = 0; if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, 1, &file, -1); result = strcmp(ptr, file); g_free(file); if (result == 0) return pos; pos++; } while (gtk_tree_model_iter_next(model, &iter)); } /* 将文件加入model */ if (access(pathname, F_OK) != 0) { theme = gtk_icon_theme_get_default(); file = iptux_erase_filename_suffix(pathname); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); } else pixbuf = gdk_pixbuf_new_from_file_at_size(pathname, MAX_ICONSIZE, MAX_ICONSIZE, NULL); if (pixbuf) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, ptr, -1); g_object_unref(pixbuf); } else pos = -1; return pos; } /** * 弹出选择项的菜单. * @param treeview tree-view * @param event event * @return Gtk+库所需 */ gboolean DataSettings::PopupPickMenu(GtkWidget *treeview, GdkEventButton *event) { GtkWidget *menu; GtkTreeModel *model; if (event->button != 3) return FALSE; model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); menu = CreatePopupMenu(model); gtk_widget_show_all(menu); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event->button, event->time); return TRUE; } /** * 添加新的头像数据. * @param button button * @param widset widget set */ void DataSettings::AddNewIcon(GtkWidget *button, GData **widset) { GtkWidget *parent, *combo; GtkTreeModel *model; gchar *filename; gint active; parent = GTK_WIDGET(g_datalist_get_data(widset, "dialog-widget")); if (!(filename = choose_file_with_preview(_("Please select a face picture"), parent))) return; combo = GTK_WIDGET(g_object_get_data(G_OBJECT(button), "icon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(combo)); active = IconfileGetItemPos(model, filename); gtk_combo_box_set_active(GTK_COMBO_BOX(combo), active); g_free(filename); } /** * 选择个人形象照片. * @param widset widget set */ void DataSettings::ChoosePhoto(GData **widset) { GtkWidget *image, *parent; GdkPixbuf *pixbuf; gchar path[MAX_PATHLEN]; gchar *filename; parent = GTK_WIDGET(g_datalist_get_data(widset, "dialog-widget")); if (!(filename = choose_file_with_preview(_("Please select a personal photo"), parent))) return; if ((pixbuf = gdk_pixbuf_new_from_file(filename, NULL))) { snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH "/photo", g_get_user_config_dir()); pixbuf_shrink_scale_1(&pixbuf, MAX_PHOTOSIZE, MAX_PHOTOSIZE); gdk_pixbuf_save(pixbuf, path, "bmp", NULL, NULL); //命中率极高,不妨直接保存 image = GTK_WIDGET(g_datalist_get_data(widset, "photo-image-widget")); pixbuf_shrink_scale_1(&pixbuf, MAX_PREVIEWSIZE, MAX_PREVIEWSIZE); gtk_image_set_from_pixbuf(GTK_IMAGE(image), pixbuf); g_object_unref(pixbuf); } g_free(filename); } /** * 根据(chkbutton)的状态来设置(widget)的灵敏度. * @param chkbutton check-button * @param widget widget */ void DataSettings::AdjustSensitive(GtkWidget *chkbutton, GtkWidget *widget) { if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(chkbutton))) gtk_widget_set_sensitive(widget, TRUE); else gtk_widget_set_sensitive(widget, FALSE); } /** * 调整声音系统的音量. * @param hscale hscale */ void DataSettings::AdjustVolume(GtkWidget *hscale) { gdouble value; value = gtk_range_get_value(GTK_RANGE(hscale)); g_sndsys->AdjustVolume(value); } /** * 声音树(sound-tree)选中项变更的响应函数. * @param selection tree-selection * @param widset widget set */ void DataSettings::SndtreeSelectItemChanged(GtkTreeSelection *selection, GData **widset) { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gchar *path; gtk_tree_selection_get_selected(selection, &model, &iter); gtk_tree_model_get(model, &iter, 2, &path, -1); widget = GTK_WIDGET(g_datalist_get_data(widset, "sound-chooser-widget")); gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(widget), path); g_free(path); } /** * 重设声音文件的响应函数. * @param chooser file-chooser * @param widset widget set */ void DataSettings::ChooserResetSndtree(GtkWidget *chooser, GData **widset) { GtkWidget *treeview; GtkTreeSelection *selection; GtkTreeModel *model; GtkTreeIter iter; gchar *path; treeview = GTK_WIDGET(g_datalist_get_data(widset, "sound-treeview-widget")); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview)); path = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(chooser)); gtk_tree_selection_get_selected(selection, &model, &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 2, path, -1); g_free(path); } /** * 播放测试. * @param widset widget set */ void DataSettings::PlayTesting(GData **widset) { GtkWidget *widget; gchar *path; widget = GTK_WIDGET(g_datalist_get_data(widset, "sound-chooser-widget")); path = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(widget)); g_sndsys->Playing(path); g_free(path); } /** * 停止播放测试. */ void DataSettings::StopTesting() { g_sndsys->Stop(); } /** * 网络树(network-tree)排序比较函数. * @param model network-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint DataSettings::NetworkTreeCompareFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { gchar *atext, *btext; gint result; gtk_tree_model_get(model, a, 0, &atext, -1); gtk_tree_model_get(model, b, 0, &btext, -1); result = strcmp(atext, btext); g_free(atext); g_free(btext); return result; } /** * 增加一个IP网段. * @param widset widget set */ void DataSettings::ClickAddIpseg(GData **widset) { GtkWidget *startentry, *endentry, *treeview, *parent; GtkTreeModel *model; GtkTreeIter iter; const gchar *starttext, *endtext; in_addr_t startip, endip; /* 合法性检查 */ parent = GTK_WIDGET(g_datalist_get_data(widset, "dialog-widget")); startentry = GTK_WIDGET(g_datalist_get_data(widset, "startip-entry-widget")); starttext = gtk_entry_get_text(GTK_ENTRY(startentry)); if (inet_pton(AF_INET, starttext, &startip) <= 0) { gtk_widget_grab_focus(startentry); pop_warning(parent, _("\nIllegal IP(v4) address: %s!"), starttext); return; } endentry = GTK_WIDGET(g_datalist_get_data(widset, "endip-entry-widget")); endtext = gtk_entry_get_text(GTK_ENTRY(endentry)); if (inet_pton(AF_INET, endtext, &endip) <= 0) { gtk_widget_grab_focus(endentry); pop_warning(parent, _("\nIllegal IP(v4) address: %s!"), endtext); return; } /* 加入网段树 */ startip = ntohl(startip); endip = ntohl(endip); treeview = GTK_WIDGET(g_datalist_get_data(widset, "network-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_list_store_append(GTK_LIST_STORE(model), &iter); if (startip <= endip) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, starttext, 1, endtext, -1); else gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, endtext, 1, starttext, -1); /* 扫尾 */ gtk_widget_grab_focus(startentry); gtk_entry_set_text(GTK_ENTRY(startentry), "\0"); gtk_entry_set_text(GTK_ENTRY(endentry), "\0"); } /** * 删除一个IP网段. * @param widset widget set */ void DataSettings::ClickDelIpseg(GData **widset) { GtkWidget *startentry, *endentry, *treeview; GtkTreeSelection *selection; GtkTreeModel *model; GtkTreeIter iter; gchar *starttext, *endtext; treeview = GTK_WIDGET(g_datalist_get_data(widset, "network-treeview-widget")); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview)); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); if (!gtk_tree_model_get_iter_first(model, &iter)) return; /* 删除所有被选中的项,并提取第一项数据 */ starttext = endtext = NULL; do { mark: if (gtk_tree_selection_iter_is_selected(selection, &iter)) { if (!starttext) gtk_tree_model_get(model, &iter, 0, &starttext, 1, &endtext, -1); if (gtk_list_store_remove(GTK_LIST_STORE(model), &iter)) goto mark; break; } } while (gtk_tree_model_iter_next(model, &iter)); /* 把第一项数据填入输入框 */ if (!starttext) return; startentry = GTK_WIDGET(g_datalist_get_data(widset, "startip-entry-widget")); gtk_entry_set_text(GTK_ENTRY(startentry), starttext); g_free(starttext); endentry = GTK_WIDGET(g_datalist_get_data(widset, "endip-entry-widget")); gtk_entry_set_text(GTK_ENTRY(endentry), endtext); g_free(endtext); } /** * 编辑cell. * @param renderer cell-renderer-text * @param path item-path * @param newtext new-text * @param model model */ void DataSettings::CellEditText(GtkCellRendererText *renderer, gchar *path, gchar *newtext, GtkTreeModel *model) { GtkTreeIter iter; gint number; gtk_tree_model_get_iter_from_string(model, &iter, path); number = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(renderer), "column-number")); gtk_list_store_set(GTK_LIST_STORE(model), &iter, number, newtext, -1); } /** * 导入网段数据. * @param dset 数据设置类 */ void DataSettings::ImportNetSegment(DataSettings *dset) { GtkWidget *dialog, *parent; GtkTreeModel *model; GtkTreeIter iter; gchar *filename; GSList *list, *tlist; NetSegment *pns; parent = GTK_WIDGET(g_datalist_get_data(&dset->widset, "dialog-widget")); dialog = gtk_file_chooser_dialog_new( _("Please select a file to import data"), GTK_WINDOW(parent), GTK_FILE_CHOOSER_ACTION_OPEN, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog), g_get_home_dir()); switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_ACCEPT: model = GTK_TREE_MODEL(g_datalist_get_data(&dset->mdlset, "network-model")); gtk_list_store_clear(GTK_LIST_STORE(model)); list = NULL; filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog)); dset->ReadNetSegment(filename, &list); g_free(filename); tlist = list; while (tlist) { pns = (NetSegment *)tlist->data; gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pns->startip, 1, pns->endip, 2, pns->description, -1); tlist = g_slist_next(tlist); } for (tlist = list; tlist; tlist = g_slist_next(tlist)) delete (NetSegment *)tlist->data; g_slist_free(list); default: break; } gtk_widget_destroy(dialog); } /** * 导出网段数据. * @param dset 数据设置类 */ void DataSettings::ExportNetSegment(DataSettings *dset) { GtkWidget *dialog, *parent; GtkTreeModel *model; GtkTreeIter iter; gchar *filename; GSList *list, *tlist; NetSegment *ns; parent = GTK_WIDGET(g_datalist_get_data(&dset->widset, "dialog-widget")); dialog = gtk_file_chooser_dialog_new( _("Save data to file"), GTK_WINDOW(parent), GTK_FILE_CHOOSER_ACTION_SAVE, GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog), g_get_home_dir()); switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_ACCEPT: model = GTK_TREE_MODEL(g_datalist_get_data(&dset->mdlset, "network-model")); if (!gtk_tree_model_get_iter_first(model, &iter)) break; list = NULL; do { ns = new NetSegment; gtk_tree_model_get(model, &iter, 0, &ns->startip, 1, &ns->endip, 2, &ns->description, -1); list = g_slist_append(list, ns); } while (gtk_tree_model_iter_next(model, &iter)); filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog)); dset->WriteNetSegment(filename, list); g_free(filename); for (tlist = list; tlist; tlist = g_slist_next(tlist)) delete (NetSegment *)tlist->data; g_slist_free(list); default: break; } gtk_widget_destroy(dialog); } /** * 清空网段数据. * @param mdlset model set */ void DataSettings::ClearNetSegment(GData **mdlset) { GtkTreeModel *model; model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "network-model")); gtk_list_store_clear(GTK_LIST_STORE(model)); } } // namespace iptux iptux-0.7.4/src/iptux/DataSettings.h000066400000000000000000000054261323207530100174010ustar00rootroot00000000000000// // C++ Interface: DataSettings // // Description:程序功能、数据设置 // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DATASETTINGS_H #define IPTUX_DATASETTINGS_H #include "iptux/mess.h" namespace iptux { class DataSettings { public: DataSettings(); ~DataSettings(); static void ResetDataEntry(GtkWidget *parent); private: void InitSublayer(); void ClearSublayer(); GtkWidget *CreateMainDialog(GtkWidget *parent); GtkWidget *CreatePersonal(); GtkWidget *CreateSystem(); GtkWidget *CreateSound(); GtkWidget *CreateNetwork(); void SetPersonalValue(); void SetSystemValue(); void SetSoundValue(); void SetNetworkValue(); GtkTreeModel *CreateIconModel(); GtkTreeModel *CreateSndModel(); GtkTreeModel *CreateNetworkModel(); void FillIconModel(GtkTreeModel *model); void FillSndModel(GtkTreeModel *model); void FillNetworkModel(GtkTreeModel *model); GtkWidget *CreateIconTree(GtkTreeModel *model); GtkWidget *CreateSndTree(GtkTreeModel *model); GtkWidget *CreateNetworkTree(GtkTreeModel *model); GtkWidget *CreateArchiveChooser(); GtkWidget *CreateFontChooser(); GtkWidget *CreateSndChooser(); GData *widset; //窗体集 GData *mdlset; //数据model集 private: void ObtainPersonalValue(); void ObtainSystemValue(); void ObtainSoundValue(); void ObtainNetworkValue(); void WriteNetSegment(const char *filename, GSList *list); void ReadNetSegment(const char *filename, GSList **list); static GtkWidget *CreatePopupMenu(GtkTreeModel *model); static gint IconfileGetItemPos(GtkTreeModel *model, const char *pathname); //回调处理部分 private: static gboolean PopupPickMenu(GtkWidget *treeview, GdkEventButton *event); static void AddNewIcon(GtkWidget *button, GData **widset); static void ChoosePhoto(GData **widset); static void AdjustSensitive(GtkWidget *chkbutton, GtkWidget *widget); static void AdjustVolume(GtkWidget *hscale); static void SndtreeSelectItemChanged(GtkTreeSelection *selection, GData **widset); static void ChooserResetSndtree(GtkWidget *chooser, GData **widset); static void PlayTesting(GData **widset); static void StopTesting(); static gint NetworkTreeCompareFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); static void ClickAddIpseg(GData **widset); static void ClickDelIpseg(GData **widset); static void CellEditText(GtkCellRendererText *renderer, gchar *path, gchar *newtext, GtkTreeModel *model); static void ImportNetSegment(DataSettings *dset); static void ExportNetSegment(DataSettings *dset); static void ClearNetSegment(GData **mdlset); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/DetectPal.cpp000066400000000000000000000064361323207530100172110ustar00rootroot00000000000000// // C++ Implementation: DetectPal // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "DetectPal.h" #include "iptux/Command.h" #include "iptux/CoreThread.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/output.h" namespace iptux { /** * 类构造函数. */ DetectPal::DetectPal() : widset(NULL) { g_datalist_init(&widset); } /** * 类析构函数. */ DetectPal::~DetectPal() { g_datalist_clear(&widset); } /** * 探测好友入口. * @param parent 父窗口指针 */ void DetectPal::DetectEntry(GtkWidget *parent) { GtkWidget *dialog; DetectPal dpal; /* 创建对话框窗体 */ dialog = dpal.CreateMainDialog(parent); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), dpal.CreateInputArea(), TRUE, TRUE, 0); /* 运行对话框 */ gtk_widget_show_all(dialog); mark: switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_ACCEPT: dpal.SendDetectPacket(); goto mark; default: break; } gtk_widget_destroy(dialog); } /** * 创建主对话框. * @param parent 父窗口指针 * @return 对话框 */ GtkWidget *DetectPal::CreateMainDialog(GtkWidget *parent) { GtkWidget *dialog; dialog = gtk_dialog_new_with_buttons( _("Detect pals"), GTK_WINDOW(parent), GtkDialogFlags(GTK_DIALOG_MODAL), _("Detect"), GTK_RESPONSE_ACCEPT, _("Cancel"), GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); gtk_container_set_border_width(GTK_CONTAINER(dialog), 5); g_datalist_set_data(&widset, "dialog-widget", dialog); return dialog; } /** * 创建接受输入区域. * @return 主窗体 */ GtkWidget *DetectPal::CreateInputArea() { GtkWidget *frame; GtkWidget *widget; frame = gtk_frame_new(_("Please input an IP address (IPv4 only):")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); widget = gtk_entry_new(); gtk_entry_set_max_length(GTK_ENTRY(widget), INET_ADDRSTRLEN); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_container_add(GTK_CONTAINER(frame), widget); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Please input an IP address (IPv4 only)!")); g_signal_connect(widget, "insert-text", G_CALLBACK(entry_insert_numeric), NULL); g_datalist_set_data(&widset, "ipv4-entry-widget", widget); return frame; } /** * 发送探测数据包. */ void DetectPal::SendDetectPacket() { GtkWidget *widget, *parent; Command cmd; in_addr_t ipv4; const char *text; parent = GTK_WIDGET(g_datalist_get_data(&widset, "dialog-widget")); widget = GTK_WIDGET(g_datalist_get_data(&widset, "ipv4-entry-widget")); gtk_widget_grab_focus(widget); //为下一次任务做准备 text = gtk_entry_get_text(GTK_ENTRY(widget)); if (inet_pton(AF_INET, text, &ipv4) <= 0) { pop_warning(parent, _("\nIllegal IP(v4) address: %s!"), text); return; } cmd.SendDetectPacket(g_cthrd->UdpSockQuote(), ipv4); pop_info(parent, _("The notification has been sent to %s."), text); gtk_entry_set_text(GTK_ENTRY(widget), ""); } } // namespace iptux iptux-0.7.4/src/iptux/DetectPal.h000066400000000000000000000010551323207530100166460ustar00rootroot00000000000000// // C++ Interface: DetectPal // // Description:探测好友 // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DETECTPAL_H #define IPTUX_DETECTPAL_H #include namespace iptux { class DetectPal { public: DetectPal(); ~DetectPal(); static void DetectEntry(GtkWidget *parent); private: GtkWidget *CreateMainDialog(GtkWidget *parent); GtkWidget *CreateInputArea(); void SendDetectPacket(); GData *widset; }; } // namespace iptux #endif iptux-0.7.4/src/iptux/DialogBase.cpp000066400000000000000000000722571323207530100173420ustar00rootroot00000000000000// // C++ Implementation: DialogBase // // Description: // 这个类是DialogPeer和DialogGroup的相同部分。尽量把相同的部分放在一起。 // // Author: Jiejing.Zhang , (C) 2010 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "DialogBase.h" #include #include #include "iptux/AnalogFS.h" #include "iptux/Command.h" #include "iptux/HelpDialog.h" #include "iptux/LogSystem.h" #include "iptux/SendFile.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/output.h" #include "iptux/support.h" #include "iptux/utils.h" namespace iptux { DialogBase::DialogBase(GroupInfo *grp, ProgramData &progdt) : progdt(progdt), widset(NULL), mdlset(NULL), dtset(NULL), accel(NULL), grpinf(grp), totalsendsize(0), timersend(0) { InitSublayerGeneral(); } DialogBase::~DialogBase() { if (timersend > 0) g_source_remove(timersend); ClearSublayerGeneral(); } /** * 初始化底层数据. */ void DialogBase::InitSublayerGeneral() { g_datalist_init(&widset); g_datalist_init(&mdlset); g_datalist_init(&dtset); accel = gtk_accel_group_new(); } /** * 清空底层数据. */ void DialogBase::ClearSublayerGeneral() { if (progdt.IsAutoCleanChatHistory()) { ClearHistoryTextView(); } grpinf->dialog = NULL; g_datalist_clear(&widset); g_datalist_clear(&mdlset); g_datalist_clear(&dtset); g_object_unref(accel); } /** * 清空聊天历史记录. */ void DialogBase::ClearHistoryTextView() { GtkWidget *widget; GtkTextBuffer *buffer; GtkTextTagTable *table; GtkTextIter start, end; GSList *taglist, *tlist; widget = GTK_WIDGET(g_datalist_get_data(&widset, "history-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); table = gtk_text_buffer_get_tag_table(buffer); /* 清除用于局部标记的GtkTextTag */ gtk_text_buffer_get_bounds(buffer, &start, &end); while (!gtk_text_iter_equal(&start, &end)) { tlist = taglist = gtk_text_iter_get_tags(&start); while (tlist) { /* 如果没有"global"标记,则表明此tag为局部标记,可以移除 */ if (!g_object_get_data(G_OBJECT(tlist->data), "global")) gtk_text_tag_table_remove(table, GTK_TEXT_TAG(tlist->data)); tlist = g_slist_next(tlist); } g_slist_free(taglist); gtk_text_iter_forward_char(&start); } /* 清除内容 */ gtk_text_buffer_get_bounds(buffer, &start, &end); gtk_text_buffer_delete(buffer, &start, &end); } /** * 滚动聊天历史记录区. */ void DialogBase::ScrollHistoryTextview() { GtkWidget *widget; GtkTextBuffer *buffer; GtkTextIter end; GtkTextMark *mark; widget = GTK_WIDGET(g_datalist_get_data(&widset, "history-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); gtk_text_buffer_get_end_iter(buffer, &end); mark = gtk_text_buffer_create_mark(buffer, NULL, &end, FALSE); gtk_text_view_scroll_to_mark(GTK_TEXT_VIEW(widget), mark, 0.0, TRUE, 0.0, 0.0); gtk_text_buffer_delete_mark(buffer, mark); } /** * 窗口打开情况下,新消息来到以后的接口 */ void DialogBase::OnNewMessageComing() { this->NotifyUser(); this->ScrollHistoryTextview(); } /** * 在窗口打开并且没有设置为最顶端的窗口时候,用窗口在任务栏的闪动来提示用户 */ void DialogBase::NotifyUser() { GtkWindow *window; window = GTK_WINDOW(g_datalist_get_data(&widset, "window-widget")); if (!gtk_window_has_toplevel_focus(window)) gtk_window_set_urgency_hint(window, TRUE); } /** * 添加附件. * @param list 文件链表 */ void DialogBase::AttachEnclosure(const GSList *list) { GtkWidget *widget, *pbar; GtkTreeModel *model; GtkTreeIter iter; GdkPixbuf *pixbuf, *rpixbuf, *dpixbuf; struct stat st; const GSList *tlist, *pallist; AnalogFS afs; int64_t filesize; char *filename, *filepath, *progresstip; FileInfo *file; uint32_t filenum = 0; /* 获取文件图标 */ rpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_FILE); dpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_DIRECTORY); /* 插入附件树 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "file-send-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); tlist = list; while (tlist) { if (stat((const char *)tlist->data, &st) == -1 || !(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode))) { tlist = g_slist_next(tlist); continue; } /* 获取文件类型图标 */ if (S_ISREG(st.st_mode)) pixbuf = rpixbuf; else if (S_ISDIR(st.st_mode)) pixbuf = dpixbuf; else pixbuf = NULL; filesize = afs.ftwsize((char *)tlist->data); filename = ipmsg_get_filename_me((char *)tlist->data, &filepath); pallist = GetSelPal(); while (pallist) { file = new FileInfo; file->fileid = g_cthrd->PrnQuote()++; /* file->packetn = 0;//没必要设置此字段 */ file->fileattr = S_ISREG(st.st_mode) ? IPMSG_FILE_REGULAR : IPMSG_FILE_DIR; file->filesize = filesize; file->filepath = g_strdup((char *)tlist->data); file->filectime = uint32_t(st.st_ctime); file->filenum = filenum; file->fileown = (PalInfo *)(pallist->data); /* 加入文件信息到中心节点 */ g_cthrd->Lock(); g_cthrd->AttachFileToPrivate(file); g_cthrd->Unlock(); /* 添加数据 */ gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, filename, 2, numeric_to_size(filesize), 3, tlist->data, 4, file, 5, file->fileown->name, -1); pallist = g_slist_next(pallist); } filenum++; /* 转到下一个文件节点 */ tlist = g_slist_next(tlist); } //计算待发送文件总计大小 totalsendsize = 0; gtk_tree_model_get_iter_first(model, &iter); do { //遍历待发送model gtk_tree_model_get(model, &iter, 4, &file, -1); totalsendsize += file->filesize; } while (gtk_tree_model_iter_next(model, &iter)); /* 释放文件图标 */ if (rpixbuf) g_object_unref(rpixbuf); if (dpixbuf) g_object_unref(dpixbuf); pbar = GTK_WIDGET(g_datalist_get_data(&widset, "file-send-progress-bar-widget")); progresstip = g_strdup_printf(_("%s To Send."), numeric_to_size(totalsendsize)); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), _(progresstip)); g_free(progresstip); } /* * 主窗口的信号连接 */ void DialogBase::MainWindowSignalSetup(GtkWidget *window) { g_object_set_data(G_OBJECT(window), "session-class", this); g_signal_connect_swapped(window, "destroy", G_CALLBACK(DialogDestory), this); g_signal_connect_swapped(window, "drag-data-received", G_CALLBACK(DragDataReceived), this); g_signal_connect(window, "configure-event", G_CALLBACK(WindowConfigureEvent), &dtset); g_signal_connect(window, "focus-in-event", G_CALLBACK(ClearNotify), NULL); } /** * 创建消息输入区域. * @return 主窗体 */ GtkWidget *DialogBase::CreateInputArea() { GtkWidget *frame, *box, *sw; GtkWidget *hbb, *button; GtkWidget *widget, *window; frame = gtk_frame_new(NULL); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); box = gtk_vbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(frame), box); /* 接受输入 */ sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(box), sw, TRUE, TRUE, 0); widget = gtk_text_view_new(); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(widget), GTK_WRAP_WORD); gtk_drag_dest_add_uri_targets(widget); gtk_container_add(GTK_CONTAINER(sw), widget); g_signal_connect_swapped(widget, "drag-data-received", G_CALLBACK(DragDataReceived), this); g_datalist_set_data(&widset, "input-textview-widget", widget); /* 功能按钮 */ window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); hbb = gtk_hbutton_box_new(); gtk_button_box_set_layout(GTK_BUTTON_BOX(hbb), GTK_BUTTONBOX_END); gtk_box_pack_start(GTK_BOX(box), hbb, FALSE, FALSE, 0); button = gtk_button_new_with_label(_("Close")); gtk_box_pack_end(GTK_BOX(hbb), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(gtk_widget_destroy), window); button = gtk_button_new_with_label(_("Send")); gtk_widget_add_accelerator( button, "clicked", accel, GDK_KEY_Return, progdt.IsEnterSendMessage() ? GdkModifierType(0) : GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); gtk_box_pack_end(GTK_BOX(hbb), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(SendMessage), this); return frame; } /** * 创建聊天历史记录区域. * @return 主窗体. */ GtkWidget *DialogBase::CreateHistoryArea() { GtkWidget *frame, *sw; GtkWidget *widget; frame = gtk_frame_new(_("Chat History")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_container_add(GTK_CONTAINER(frame), sw); widget = gtk_text_view_new_with_buffer(grpinf->buffer); gtk_text_view_set_cursor_visible(GTK_TEXT_VIEW(widget), FALSE); gtk_text_view_set_editable(GTK_TEXT_VIEW(widget), FALSE); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(widget), GTK_WRAP_WORD); gtk_container_add(GTK_CONTAINER(sw), widget); g_signal_connect(widget, "key-press-event", G_CALLBACK(textview_key_press_event), NULL); g_signal_connect(widget, "event-after", G_CALLBACK(textview_event_after), NULL); g_signal_connect(widget, "motion-notify-event", G_CALLBACK(textview_motion_notify_event), NULL); g_signal_connect(widget, "visibility-notify-event", G_CALLBACK(textview_visibility_notify_event), NULL); g_datalist_set_data(&widset, "history-textview-widget", widget); /* 滚动消息到最末位置 */ ScrollHistoryTextview(); return frame; } /** * 创建文件菜单. * @return 菜单 */ GtkWidget *DialogBase::CreateFileMenu() { GtkWidget *menushell, *window, *treeview; GtkWidget *menu, *menuitem; window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); menushell = gtk_menu_item_new_with_mnemonic(_("_File")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_menu_item_new_with_label(_("Attach File")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AttachRegular), this); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_S, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_menu_item_new_with_label(_("Attach Folder")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AttachFolder), this); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_D, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); treeview = GTK_WIDGET(g_datalist_get_data(&widset, "file-send-treeview-widget")); menuitem = gtk_menu_item_new_with_label(_("Remove Selected")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(RemoveSelectedFromTree), treeview); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_R, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_tearoff_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Close")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(gtk_widget_destroy), window); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_W, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); g_datalist_set_data(&widset, "file-menu", menu); return menushell; } /** * 创建帮助菜单. * @return 菜单 */ GtkWidget *DialogBase::CreateHelpMenu() { GtkWidget *menushell; GtkWidget *menu, *menuitem; menushell = gtk_menu_item_new_with_mnemonic(_("_Help")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_image_menu_item_new_from_stock(GTK_STOCK_ABOUT, accel); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect(menuitem, "activate", G_CALLBACK(HelpDialog::AboutEntry), NULL); return menushell; } /** * 选择附件. * @param fileattr 文件类型 * @return 文件链表 */ GSList *DialogBase::PickEnclosure(uint32_t fileattr) { GtkWidget *dialog, *parent; GtkFileChooserAction action; const char *title; GSList *list; if (GET_MODE(fileattr) == IPMSG_FILE_REGULAR) { action = GTK_FILE_CHOOSER_ACTION_OPEN; title = _("Choose enclosure files"); } else { action = GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER; title = _("Choose enclosure folders"); } parent = GTK_WIDGET(g_datalist_get_data(&widset, "dialog-widget")); dialog = gtk_file_chooser_dialog_new( title, GTK_WINDOW(parent), action, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(dialog), FALSE); gtk_file_chooser_set_select_multiple(GTK_FILE_CHOOSER(dialog), TRUE); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog), g_get_home_dir()); switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_ACCEPT: list = gtk_file_chooser_get_filenames(GTK_FILE_CHOOSER(dialog)); break; case GTK_RESPONSE_CANCEL: default: list = NULL; break; } gtk_widget_destroy(dialog); return list; } /** * 发送附件消息. * @return 是否发送数据 */ bool DialogBase::SendEnclosureMsg() { GtkWidget *treeview; GtkTreeModel *model; GtkTreeIter iter; GSList *list; gchar *filepath; FileInfo *file; treeview = GTK_WIDGET(g_datalist_get_data(&widset, "file-send-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); if (!gtk_tree_model_get_iter_first(model, &iter)) return false; /* 获取文件并发送 */ list = NULL; do { gtk_tree_model_get(model, &iter, 3, &filepath, 4, &file, -1); list = g_slist_append(list, file); } while (gtk_tree_model_iter_next(model, &iter)); BroadcastEnclosureMsg(list); g_slist_free(list); timersend = gdk_threads_add_timeout(400, (GSourceFunc)UpdateFileSendUI, this); return true; } /** * 回馈消息. * @param msg 消息 */ void DialogBase::FeedbackMsg(const gchar *msg) { MsgPara para; ChipData *chip; /* 构建消息封装包 */ para.pal = NULL; para.stype = MESSAGE_SOURCE_TYPE_SELF; para.btype = grpinf->type; chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_STRING; chip->data = g_strdup(msg); para.dtlist = g_slist_append(NULL, chip); /* 交给某人处理吧 */ g_cthrd->InsertMsgToGroupInfoItem(grpinf, ¶); } /** * 添加常规文件附件. * @param dlgpr 对话框类 */ void DialogBase::AttachRegular(DialogBase *dlgpr) { GSList *list; if (!(list = dlgpr->PickEnclosure(IPMSG_FILE_REGULAR))) return; dlgpr->AttachEnclosure(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); } /** * 添加目录文件附件. * @param dlgpr 对话框类 */ void DialogBase::AttachFolder(DialogBase *dlgpr) { GSList *list; if (!(list = dlgpr->PickEnclosure(IPMSG_FILE_DIR))) return; dlgpr->AttachEnclosure(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); } /** * 清空聊天历史记录缓冲区. * @param dlgpr 对话框类 */ void DialogBase::ClearHistoryBuffer(DialogBase *dlgpr) { dlgpr->ClearHistoryTextView(); } /** * 发送消息. * @param dlgpr 对话框类 */ void DialogBase::SendMessage(DialogBase *dlgpr) { dlgpr->SendEnclosureMsg(); dlgpr->SendTextMsg(); dlgpr->ScrollHistoryTextview(); } /** * 对话框被摧毁的回调函数 * @param dialog */ void DialogBase::DialogDestory(DialogBase *dialog) { delete dialog; } /** * 清除提示,这个提示只是窗口闪动的提示 */ gboolean DialogBase::ClearNotify(GtkWidget *window, GdkEventConfigure *event) { if (gtk_window_get_urgency_hint(GTK_WINDOW(window))) gtk_window_set_urgency_hint(GTK_WINDOW(window), FALSE); return FALSE; } /** * 拖拽事件响应函数. * @param dlgpr 对话框类 * @param context the drag context * @param x where the drop happened * @param y where the drop happened * @param data the received data * @param info the info that has been registered with the target in the * GtkTargetList * @param time the timestamp at which the data was received */ void DialogBase::DragDataReceived(DialogBase *dlgpr, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time) { GtkWidget *widget; GSList *list; if (!ValidateDragData(data, context, time)) { return; } list = selection_data_get_path(data); //获取所有文件 dlgpr->AttachEnclosure(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); widget = GTK_WIDGET(g_datalist_get_data(&dlgpr->widset, "enclosure-frame-widget")); gtk_widget_show(widget); gtk_drag_finish(context, TRUE, FALSE, time); } /** * 主对话框位置&大小改变的响应处理函数. * @param window 主窗口 * @param event the GdkEventConfigure which triggered this signal * @param dtset data set * @return Gtk+库所需 */ gboolean DialogBase::WindowConfigureEvent(GtkWidget *window, GdkEventConfigure *event, GData **dtset) { g_datalist_set_data(dtset, "window-width", GINT_TO_POINTER(event->width)); g_datalist_set_data(dtset, "window-height", GINT_TO_POINTER(event->height)); return FALSE; } /** * 分割面板的分割位置改变的响应处理函数. * @param paned paned * @param pspec he GParamSpec of the property which changed * @param dtset data set */ void DialogBase::PanedDivideChanged(GtkWidget *paned, GParamSpec *pspec, GData **dtset) { const gchar *identify; gint position; identify = (const gchar *)g_object_get_data(G_OBJECT(paned), "position-name"); position = gtk_paned_get_position(GTK_PANED(paned)); g_datalist_set_data(dtset, identify, GINT_TO_POINTER(position)); } /** *删除选定附件. * @param dlgpr 对话框类 */ void DialogBase::RemoveSelectedFromTree(GtkWidget *widget) { GList *list; GtkTreeSelection *TreeSel; GtkTreePath *path; GtkTreeModel *model; gchar *str_data; gboolean valid = 0; GtkTreeIter iter; model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); TreeSel = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); list = gtk_tree_selection_get_selected_rows(TreeSel, NULL); if (!list) return; while (list) { gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &iter, (GtkTreePath *)g_list_nth(list, 0)->data); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 2, "delete", -1); list = g_list_next(list); } g_list_free(list); valid = gtk_tree_model_get_iter_first(GTK_TREE_MODEL(model), &iter); path = gtk_tree_model_get_path(GTK_TREE_MODEL(model), &iter); while (valid) { gtk_tree_model_get(GTK_TREE_MODEL(model), &iter, 2, &str_data, -1); if (!g_strcmp0(str_data, "delete")) gtk_list_store_remove(GTK_LIST_STORE(model), &iter); else gtk_tree_path_next(path); valid = gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &iter, path); } } /** *显示附件的TreeView的弹出菜单回调函数. * @param widget TreeView * @param event 事件 */ gint DialogBase::EncosureTreePopup(GtkWidget *treeview, GdkEvent *event) { GtkWidget *menu, *menuitem; GdkEventButton *event_button; menu = gtk_menu_new(); menuitem = gtk_menu_item_new_with_label(_("Remove Selected")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(RemoveSelectedEnclosure), treeview); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); if (event->type == GDK_BUTTON_PRESS) { event_button = (GdkEventButton *)event; if (event_button->button == 3) { gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event_button->button, event_button->time); gtk_widget_show(menuitem); return TRUE; } } return FALSE; } /** *从显示附件的TreeView删除选定行. * @param widget TreeView */ void DialogBase::RemoveSelectedEnclosure(GtkWidget *widget) { GtkTreeModel *model; GtkTreeSelection *TreeSel; GtkTreeIter iter; FileInfo *file; DialogBase *dlg; GList *list; dlg = (DialogBase *)(g_object_get_data(G_OBJECT(widget), "dialog")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); //从中心结点删除 TreeSel = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); list = gtk_tree_selection_get_selected_rows(TreeSel, NULL); if (!list) return; while (list) { gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &iter, (GtkTreePath *)g_list_nth(list, 0)->data); gtk_tree_model_get(model, &iter, 4, &file, -1); dlg->totalsendsize -= file->filesize; g_cthrd->DelFileFromPrivate(file->fileid); list = g_list_next(list); } g_list_free(list); //从列表中删除 RemoveSelectedFromTree(widget); //重新计算待发送文件大小 dlg->UpdateFileSendUI(dlg); } /** * 创建文件发送区域. * @return 主窗体 */ GtkWidget *DialogBase::CreateFileSendArea() { GtkWidget *frame, *hbox, *vbox, *button, *pbar, *sw, *treeview; GtkTreeModel *model; frame = gtk_frame_new(_("File to send.")); g_datalist_set_data(&widset, "file-send-frame-widget", frame); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); pbar = gtk_progress_bar_new(); g_datalist_set_data(&widset, "file-send-progress-bar-widget", pbar); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), _("Sending progress.")); hbox = gtk_hbox_new(FALSE, 1); gtk_box_pack_start(GTK_BOX(hbox), pbar, TRUE, TRUE, 0); button = gtk_button_new_with_label(_("Dirs")); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, TRUE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(AttachFolder), this); button = gtk_button_new_with_label(_("Files")); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, TRUE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(AttachRegular), this); button = gtk_button_new_with_label(_("Detail")); gtk_box_pack_end(GTK_BOX(hbox), button, FALSE, TRUE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(OpenTransDlg), NULL); vbox = gtk_vbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); model = CreateFileSendModel(); treeview = CreateFileSendTree(model); g_datalist_set_data_full(&mdlset, "enclosure-model", model, GDestroyNotify(g_object_unref)); g_datalist_set_data(&widset, "file-send-treeview-widget", treeview); //保存this指针,在后面消息响应函数中用到 g_object_set_data(G_OBJECT(treeview), "dialog", this); gtk_container_add(GTK_CONTAINER(sw), treeview); gtk_box_pack_end(GTK_BOX(vbox), sw, TRUE, TRUE, 0); gtk_container_add(GTK_CONTAINER(frame), vbox); return frame; } /** * 创建待发送文件树(FileSend-tree). * @param model FileSend-model * @return 待发送文件树 */ GtkWidget *DialogBase::CreateFileSendTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeSelection *selection; GtkCellRenderer *cell; GtkTreeViewColumn *column; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE); cell = gtk_cell_renderer_pixbuf_new(); column = gtk_tree_view_column_new_with_attributes("", cell, "pixbuf", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); if (grpinf->type != GROUP_BELONG_TYPE_REGULAR) { cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("PeelName"), cell, "text", 5, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); } cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Name"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Size"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Path"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect_swapped(GTK_WIDGET(view), "button_press_event", G_CALLBACK(EncosureTreePopup), view); return view; } /** * 创建待发送文件树底层数据结构. * @return FileSend-model * 0:图标 1:文件名 2:大小(string) 3:全文件名 4:文件信息(指针) 5:接收者 * 没有专门加删除标记,用第2列作删除标记,(某行反正要删除,改就改了) */ GtkTreeModel *DialogBase::CreateFileSendModel() { GtkListStore *model; model = gtk_list_store_new(6, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER, G_TYPE_STRING); return GTK_TREE_MODEL(model); } /** * 更新本窗口文件发送UI. * @param treeview FileSend-treeview * @return FileSend-model * 让传输聊天窗口从传输状态窗口去取数据,而没有让文件数据发送类把数据传送到聊天窗口, * 这是因为考虑数据要发到本窗口,会存在窗口未打开或群聊状态等不确定因素,处理过程太复杂 */ gboolean DialogBase::UpdateFileSendUI(DialogBase *dlggrp) { GtkTreeModel *model; GtkTreeIter iter; char progresstip[MAX_BUFLEN]; GtkTreeView *treeview; GtkWidget *pbar; float progress; int64_t sentsize; GtkIconTheme *theme; GdkPixbuf *pixbuf; const char *statusfile; FileInfo *file; theme = gtk_icon_theme_get_default(); statusfile = "tip-finish"; pixbuf = gtk_icon_theme_load_icon(theme, statusfile, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); treeview = GTK_TREE_VIEW( g_datalist_get_data(&(dlggrp->widset), "file-send-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); sentsize = 0; if (gtk_tree_model_get_iter_first(model, &iter)) { do { //遍历待发送model gtk_tree_model_get(model, &iter, 4, &file, -1); if (pixbuf && (file->finishedsize == file->filesize)) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, -1); sentsize += file->finishedsize; } while (gtk_tree_model_iter_next(model, &iter)); } /* 调整进度显示UI */ gtk_tree_view_columns_autosize(GTK_TREE_VIEW(treeview)); pbar = GTK_WIDGET( g_datalist_get_data(&(dlggrp->widset), "file-send-progress-bar-widget")); if (dlggrp->totalsendsize == 0) { progress = 0; snprintf(progresstip, MAX_BUFLEN, "%s", _("Sending Progress.")); } else { progress = percent(sentsize, dlggrp->totalsendsize) / 100; snprintf(progresstip, MAX_BUFLEN, _("%s Of %s Sent."), numeric_to_size(sentsize), numeric_to_size(dlggrp->totalsendsize)); } if (progress == 1) { g_source_remove(dlggrp->timersend); gtk_list_store_clear(GTK_LIST_STORE(model)); snprintf(progresstip, MAX_BUFLEN, "%s", _("Mission Completed!")); } gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(pbar), progress); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), _(progresstip)); return TRUE; } /** * 打开文件传输窗口. * @param dlgpr 对话框类 */ void DialogBase::OpenTransDlg(DialogBase *dlgpr) { g_mwin->OpenTransWindow(); } } // namespace iptuxiptux-0.7.4/src/iptux/DialogBase.h000066400000000000000000000060361323207530100167770ustar00rootroot00000000000000// // C++ Interface: DialogBase // // Description: // 这个类是DialogPeer和DialogGroup的相同部分。尽量把相同的部分放在一起。 // // Author: // Author: cwll ,(C) 2012.02 // Jiejing.Zhang , (C) 2010 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DIALOGBASE_H #define IPTUX_DIALOGBASE_H #include "iptux/ProgramData.h" #include "iptux/mess.h" namespace iptux { class DialogBase : public SessionAbstract { public: DialogBase(GroupInfo *grp, ProgramData &progdt); virtual ~DialogBase(); protected: void InitSublayerGeneral(); void ClearSublayerGeneral(); void ClearHistoryTextView(); void ScrollHistoryTextview(); virtual void OnNewMessageComing(); void NotifyUser(); void AttachEnclosure(const GSList *list); /* UI general */ GtkWidget *CreateInputArea(); virtual GtkWidget *CreateHistoryArea(); virtual GtkWidget *CreateFileMenu(); virtual GtkWidget *CreateHelpMenu(); virtual GtkWidget *CreateFileSendArea(); virtual GtkWidget *CreateFileSendTree(GtkTreeModel *model); virtual GSList *GetSelPal() { return NULL; }; void MainWindowSignalSetup(GtkWidget *window); GtkTreeModel *CreateFileSendModel(); GSList *PickEnclosure(uint32_t fileattr); bool SendEnclosureMsg(); virtual bool SendTextMsg() = 0; /* TODO: Group SendTextMsg need add Picture */ void FeedbackMsg(const gchar *msg); virtual void BroadcastEnclosureMsg(GSList *list){}; // 回调部分 static void DialogDestory(DialogBase *); static gboolean ClearNotify(GtkWidget *window, GdkEventConfigure *event); static void DragDataReceived(DialogBase *dlgpr, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time); static void AttachRegular(DialogBase *dlgpr); static void AttachFolder(DialogBase *dlgpr); static void RemoveSelectedFromTree(GtkWidget *widget); static void ClearHistoryBuffer(DialogBase *dlgpr); static void SendMessage(DialogBase *dlggrp); static gboolean WindowConfigureEvent(GtkWidget *window, GdkEventConfigure *event, GData **dtset); static void PanedDivideChanged(GtkWidget *paned, GParamSpec *pspec, GData **dtset); static gint EncosureTreePopup(GtkWidget *widget, GdkEvent *event); static gboolean UpdateFileSendUI(DialogBase *dlggrp); static void RemoveSelectedEnclosure(GtkWidget *widget); static void OpenTransDlg(DialogBase *dlgpr); protected: ProgramData &progdt; GData *widset; //窗体集 GData *mdlset; //数据model集 GData *dtset; //通用数据集 GtkAccelGroup *accel; //快捷键组 GroupInfo *grpinf; //群组信息 int64_t totalsendsize; //总计待发送大小(包括已发送) struct timeval lasktime; //上一次更新UI的时间 guint timersend; // 发送文件界面更新计时器ID }; } // namespace iptux #endif iptux-0.7.4/src/iptux/DialogGroup.cpp000066400000000000000000000601461323207530100175560ustar00rootroot00000000000000// // C++ Implementation: DialogGroup // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "DialogGroup.h" #include "iptux/Command.h" #include "iptux/DialogPeer.h" #include "iptux/HelpDialog.h" #include "iptux/SendFile.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/output.h" #include "iptux/support.h" #include "iptux/utils.h" namespace iptux { /** * 类构造函数. * @param grp 群组信息 */ DialogGroup::DialogGroup(GroupInfo *grp, IptuxConfig &config, ProgramData &progdt) : DialogBase(grp, progdt), config(config) { InitSublayerSpecify(); } /** * 类析构函数. */ DialogGroup::~DialogGroup() { SaveUILayout(); } /** * 群组对话框入口. * @param grpinf 群组信息 */ void DialogGroup::GroupDialogEntry(IptuxConfig &config, GroupInfo *grpinf, ProgramData &progdt) { DialogGroup *dlggrp; GtkWidget *window, *widget; dlggrp = new DialogGroup(grpinf, config, progdt); window = dlggrp->CreateMainWindow(); gtk_container_add(GTK_CONTAINER(window), dlggrp->CreateAllArea()); gtk_widget_show_all(window); /* 将焦点置于文本输入框 */ widget = GTK_WIDGET(g_datalist_get_data(&dlggrp->widset, "input-textview-widget")); gtk_widget_grab_focus(widget); /* 从消息队列中移除 */ g_cthrd->Lock(); if (g_cthrd->MsglineContainItem(grpinf)) { g_mwin->MakeItemBlinking(grpinf, FALSE); g_cthrd->PopItemFromMsgline(grpinf); } g_cthrd->Unlock(); /* delete dlggrp;//请不要这样做,此类将会在窗口被摧毁后自动释放 */ } /** * 更新群组成员树(member-tree)指定项. * @param pal class PalInfo */ void DialogGroup::UpdatePalData(PalInfo *pal) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gpointer data; gchar *file; /* 查询项所在的位置,若没有则添加 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); data = NULL; //防止可能出现的(data == pal) if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, 3, &data, -1); if (data == pal) break; } while (gtk_tree_model_iter_next(model, &iter)); } if (data != pal) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, FALSE, 3, pal, -1); } /* 更新数据 */ theme = gtk_icon_theme_get_default(); file = iptux_erase_filename_suffix(pal->iconfile); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 1, pixbuf, 2, pal->name, -1); if (pixbuf) g_object_unref(pixbuf); } /** * 插入项到群组成员树(member-tree). * @param pal class PalInfo */ void DialogGroup::InsertPalData(PalInfo *pal) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gchar *file; theme = gtk_icon_theme_get_default(); file = iptux_erase_filename_suffix(pal->iconfile); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, FALSE, 1, pixbuf, 2, pal->name, 3, pal, -1); if (pixbuf) g_object_unref(pixbuf); } /** * 从群组成员树(member-tree)删除指定项. * @param pal class PalInfo */ void DialogGroup::DelPalData(PalInfo *pal) { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gpointer data; widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, 3, &data, -1); if (data == pal) { gtk_list_store_remove(GTK_LIST_STORE(model), &iter); break; } } while (gtk_tree_model_iter_next(model, &iter)); } } /** * 清除本群组所有好友数据. */ void DialogGroup::ClearAllPalData() { GtkWidget *widget; GtkTreeModel *model; widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); gtk_list_store_clear(GTK_LIST_STORE(model)); } /** * 初始化底层数据. */ void DialogGroup::InitSublayerSpecify() { GtkTreeModel *model; model = CreateMemberModel(); g_datalist_set_data_full(&mdlset, "member-model", model, GDestroyNotify(g_object_unref)); FillMemberModel(model); } /** * 写出对话框的UI布局数据. */ void DialogGroup::SaveUILayout() { config.SetInt("group_window_width", GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-width"))); config.SetInt("group_window_height", GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-height"))); config.SetInt("group_main_paned_divide", GPOINTER_TO_INT(g_datalist_get_data( &dtset, "main-paned-divide"))); config.SetInt("group_historyinput_paned_divide", GPOINTER_TO_INT( g_datalist_get_data(&dtset, "historyinput-paned-divide"))); config.SetInt("group_memberenclosure_paned_divide", GPOINTER_TO_INT(g_datalist_get_data( &dtset, "memberenclosure-paned-divide"))); } /** * 创建主窗口. * @return 窗口 */ GtkWidget *DialogGroup::CreateMainWindow() { char buf[MAX_BUFLEN]; GtkWidget *window; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); snprintf(buf, MAX_BUFLEN, _("Talk with the group %s"), grpinf->name); gtk_window_set_title(GTK_WINDOW(window), buf); gtk_window_set_default_size(GTK_WINDOW(window), config.GetInt("group_window_width", 500), config.GetInt("group_window_height", 350)); gtk_window_set_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER); gtk_window_add_accel_group(GTK_WINDOW(window), accel); g_datalist_set_data(&widset, "window-widget", window); widget_enable_dnd_uri(window); grpinf->dialog = window; MainWindowSignalSetup(window); return window; } /** * 创建所有区域. * @return 主窗体 */ GtkWidget *DialogGroup::CreateAllArea() { GtkWidget *box; GtkWidget *hpaned, *vpaned; gint position; box = gtk_vbox_new(FALSE, 0); /* 加入菜单条 */ gtk_box_pack_start(GTK_BOX(box), CreateMenuBar(), FALSE, FALSE, 0); /* 加入主区域 */ hpaned = gtk_hpaned_new(); g_object_set_data(G_OBJECT(hpaned), "position-name", (gpointer) "main-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "main-paned-divide")); gtk_paned_set_position(GTK_PANED(hpaned), position); gtk_box_pack_start(GTK_BOX(box), hpaned, TRUE, TRUE, 0); g_signal_connect(hpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); /*/* 加入组成员&附件区域 */ vpaned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "memberenclosure-paned-divide"); position = GPOINTER_TO_INT( g_datalist_get_data(&dtset, "memberenclosure-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); gtk_paned_pack1(GTK_PANED(hpaned), vpaned, FALSE, TRUE); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_paned_pack1(GTK_PANED(vpaned), CreateMemberArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(vpaned), CreateFileSendArea(), FALSE, TRUE); /*/* 加入聊天历史记录&输入区域 */ vpaned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "historyinput-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "historyinput-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); gtk_paned_pack2(GTK_PANED(hpaned), vpaned, TRUE, TRUE); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_paned_pack1(GTK_PANED(vpaned), CreateHistoryArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(vpaned), DialogBase::CreateInputArea(), FALSE, TRUE); return box; } /** * 创建菜单条. * @return 菜单条 */ GtkWidget *DialogGroup::CreateMenuBar() { GtkWidget *menubar; menubar = gtk_menu_bar_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateFileMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateToolMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateHelpMenu()); return menubar; } /** * 创建组成员区域. * @return 主窗体 */ GtkWidget *DialogGroup::CreateMemberArea() { GtkWidget *frame, *sw; GtkWidget *widget; GtkTreeModel *model; frame = gtk_frame_new(_("Member")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_container_add(GTK_CONTAINER(frame), sw); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "member-model")); widget = CreateMemberTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_signal_connect(widget, "button-press-event", G_CALLBACK(PopupPickMenu), NULL); g_signal_connect(widget, "row-activated", G_CALLBACK(MembertreeItemActivated), this); g_datalist_set_data(&widset, "member-treeview-widget", widget); return frame; } /** * 群组成员树(member-tree)底层数据结构. * 4,0 toggled,1 icon,2 nickname,3 data \n * 是否被选中;好友头像;好友昵称;好友数据 \n * @return member-model */ GtkTreeModel *DialogGroup::CreateMemberModel() { GtkListStore *model; model = gtk_list_store_new(4, G_TYPE_BOOLEAN, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_POINTER); gtk_tree_sortable_set_default_sort_func( GTK_TREE_SORTABLE(model), GtkTreeIterCompareFunc(MemberTreeCompareByNameFunc), NULL, NULL); gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); return GTK_TREE_MODEL(model); } /** * 为群组成员树(member-tree)填充底层数据. * @param model member-model */ void DialogGroup::FillMemberModel(GtkTreeModel *model) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkTreeIter iter; GSList *tlist; PalInfo *pal; char *file; theme = gtk_icon_theme_get_default(); g_cthrd->Lock(); tlist = grpinf->member; while (tlist) { pal = (PalInfo *)tlist->data; file = iptux_erase_filename_suffix(pal->iconfile); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, TRUE, 1, pixbuf, 2, pal->name, 3, pal, -1); if (pixbuf) g_object_unref(pixbuf); tlist = g_slist_next(tlist); } g_cthrd->Unlock(); } /** * 创建群组成员树(member-tree). * @param model member-model * @return 群组树 */ GtkWidget *DialogGroup::CreateMemberTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeSelection *selection; GtkCellRenderer *cell; GtkTreeViewColumn *column; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_NONE); cell = gtk_cell_renderer_toggle_new(); g_signal_connect_swapped(cell, "toggled", G_CALLBACK(model_turn_select), model); column = gtk_tree_view_column_new_with_attributes(_("Send"), cell, "active", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); column = gtk_tree_view_column_new(); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_column_set_title(column, _("Pals")); cell = gtk_cell_renderer_pixbuf_new(); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "pixbuf", 1, NULL); cell = gtk_cell_renderer_text_new(); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "text", 2, NULL); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); return view; } /** * 创建工具菜单. * @return 菜单 */ GtkWidget *DialogGroup::CreateToolMenu() { GtkWidget *menushell; GtkWidget *menu, *submenu, *menuitem; GtkTreeModel *model; model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "member-model")); menushell = gtk_menu_item_new_with_mnemonic(_("_Tools")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); /* 清空历史缓冲区 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Clear Buffer")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ClearHistoryBuffer), this); /* 群组成员排序 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Sort")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); submenu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menuitem), submenu); /*/* 按昵称排序 */ NO_OPERATION_C menuitem = gtk_radio_menu_item_new_with_label(NULL, _("By Nickname")); g_object_set_data(G_OBJECT(menuitem), "compare-func", (gpointer)MemberTreeCompareByNameFunc); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetMemberTreeSortFunc), model); /*/* 按IP地址排序 */ menuitem = gtk_radio_menu_item_new_with_label_from_widget( GTK_RADIO_MENU_ITEM(menuitem), _("By IP")); g_object_set_data(G_OBJECT(menuitem), "compare-func", (gpointer)MemberTreeCompareByIPFunc); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetMemberTreeSortFunc), model); /*/* 分割符 */ menuitem = gtk_separator_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); /*/* 升序 */ NO_OPERATION_C menuitem = gtk_radio_menu_item_new_with_label(NULL, _("Ascending")); g_object_set_data(G_OBJECT(menuitem), "sort-type", GINT_TO_POINTER(GTK_SORT_ASCENDING)); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetMemberTreeSortType), model); /*/* 降序 */ menuitem = gtk_radio_menu_item_new_with_label_from_widget( GTK_RADIO_MENU_ITEM(menuitem), _("Descending")); g_object_set_data(G_OBJECT(menuitem), "sort-type", GINT_TO_POINTER(GTK_SORT_DESCENDING)); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetMemberTreeSortType), model); return menushell; } /** * 向选中的好友广播附件消息. * @param list 文件链表 */ void DialogGroup::BroadcastEnclosureMsg(GSList *list) { SendFile sfile; GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gboolean active; PalInfo *pal; GSList *plist; /* 考察是否有成员 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (!gtk_tree_model_get_iter_first(model, &iter)) { /** * @note 链表(list)的数据本来应该由(sfile.BcstFileInfoEntry())接手的, * 既然已经没有那个机会了, 当然就只好在这儿手动释放了. */ g_slist_foreach(list, GFunc(g_free), NULL); return; } /* 向选中的成员发送附件 */ plist = NULL; do { gtk_tree_model_get(model, &iter, 0, &active, 3, &pal, -1); if (active) plist = g_slist_append(plist, pal); } while (gtk_tree_model_iter_next(model, &iter)); sfile.BcstFileInfoEntry(plist, list); g_slist_free(plist); } /** * 向选中的好友广播文本消息. * @param msg 文本消息 */ void DialogGroup::BroadcastTextMsg(const gchar *msg) { Command cmd; GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gboolean active; uint32_t opttype; PalInfo *pal; /* 考察是否有成员 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (!gtk_tree_model_get_iter_first(model, &iter)) return; /* 向选中的成员发送数据 */ do { gtk_tree_model_get(model, &iter, 0, &active, 3, &pal, -1); if (active) { if (FLAG_ISSET(pal->flags, 0)) { switch (grpinf->type) { case GROUP_BELONG_TYPE_BROADCAST: opttype = IPTUX_BROADCASTOPT; break; case GROUP_BELONG_TYPE_GROUP: opttype = IPTUX_GROUPOPT; break; case GROUP_BELONG_TYPE_SEGMENT: opttype = IPTUX_SEGMENTOPT; break; case GROUP_BELONG_TYPE_REGULAR: default: opttype = IPTUX_REGULAROPT; break; } cmd.SendUnitMsg(g_cthrd->UdpSockQuote(), pal, opttype, msg); } else cmd.SendGroupMsg(g_cthrd->UdpSockQuote(), pal, msg); } } while (gtk_tree_model_iter_next(model, &iter)); } /** * 创建选择项的弹出菜单. * @param model model * @return 菜单 */ GtkWidget *DialogGroup::CreatePopupMenu(GtkTreeModel *model) { GtkWidget *menu, *menuitem; menu = gtk_menu_new(); menuitem = gtk_menu_item_new_with_label(_("Select All")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_select_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Reverse Select")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_turn_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Clear Up")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(model_clear_all), model); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); return menu; } /** * 群组成员树(member-tree)按昵称排序的比较函数. * @param model member-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint DialogGroup::MemberTreeCompareByNameFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { PalInfo *apal, *bpal; gint result; gtk_tree_model_get(model, a, 3, &apal, -1); gtk_tree_model_get(model, b, 3, &bpal, -1); result = strcmp(apal->name, bpal->name); return result; } /** * 群组成员树(member-tree)按IP排序的比较函数. * @param model member-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint DialogGroup::MemberTreeCompareByIPFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { PalInfo *apal, *bpal; gint result; gtk_tree_model_get(model, a, 3, &apal, -1); gtk_tree_model_get(model, b, 3, &bpal, -1); result = ntohl(apal->ipv4) - ntohl(bpal->ipv4); return result; } /** * 设置群组成员树(member-tree)的比较函数. * @param menuitem radio-menu-item * @param model member-model */ void DialogGroup::SetMemberTreeSortFunc(GtkWidget *menuitem, GtkTreeModel *model) { GtkTreeIterCompareFunc func; if (!gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(menuitem))) return; func = (GtkTreeIterCompareFunc)( g_object_get_data(G_OBJECT(menuitem), "compare-func")); gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(model), func, NULL, NULL); } /** * 设置群组成员树(member-tree)的排序方式. * @param menuitem radio-menu-item * @param model member-model */ void DialogGroup::SetMemberTreeSortType(GtkWidget *menuitem, GtkTreeModel *model) { GtkSortType type; if (!gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(menuitem))) return; type = (GtkSortType)GPOINTER_TO_INT( g_object_get_data(G_OBJECT(menuitem), "sort-type")); gtk_tree_sortable_set_sort_column_id( GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, type); } /** * 弹出选择项的菜单. * @param treeview tree-view * @param event event * @return Gtk+库所需 */ gboolean DialogGroup::PopupPickMenu(GtkWidget *treeview, GdkEventButton *event) { GtkWidget *menu; GtkTreeModel *model; if (event->button != 3) return FALSE; model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); menu = CreatePopupMenu(model); gtk_widget_show_all(menu); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event->button, event->time); return TRUE; } /** * 群组成员树(member-tree)项被激活. * @param treeview tree-view * @param path path * @param column column */ void DialogGroup::MembertreeItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, DialogGroup *self) { GtkTreeModel *model; GtkTreeIter iter; PalInfo *pal; GroupInfo *grpinf; model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 3, &pal, -1); if ((grpinf = g_cthrd->GetPalRegularItem(pal))) { if ((grpinf->dialog)) gtk_window_present(GTK_WINDOW(grpinf->dialog)); else DialogPeer::PeerDialogEntry(self->config, grpinf, self->progdt); } } bool DialogGroup::SendTextMsg() { GtkWidget *textview; GtkTextBuffer *buffer; GtkTextIter start, end; MsgPara msgpara; gchar *msg; /* 考察缓冲区内是否存在数据 */ textview = GTK_WIDGET(g_datalist_get_data(&widset, "input-textview-widget")); gtk_widget_grab_focus(textview); //为下一次任务做准备 buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(textview)); gtk_text_buffer_get_bounds(buffer, &start, &end); if (gtk_text_iter_equal(&start, &end)) return false; /* 获取数据并发送 */ msg = gtk_text_buffer_get_text(buffer, &start, &end, FALSE); gtk_text_buffer_delete(buffer, &start, &end); FeedbackMsg(msg); BroadcastTextMsg(msg); msgpara.stype = MESSAGE_SOURCE_TYPE_SELF; msgpara.pal = NULL; g_lgsys->CommunicateLog(&msgpara, "[STRING]%s", msg); g_free(msg); return true; } /** * 发送消息. * @param dlggrp 对话框类 */ void DialogGroup::SendMessage(DialogGroup *dlggrp) { dlggrp->SendEnclosureMsg(); dlggrp->SendTextMsg(); } /** * 获取待发送成员列表. * @return plist 获取待发送成员列表 * 调用该函数后须free plist */ GSList *DialogGroup::GetSelPal() { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gboolean active; PalInfo *pal; GSList *plist; /* 考察是否有成员 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "member-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (!gtk_tree_model_get_iter_first(model, &iter)) return NULL; plist = NULL; do { gtk_tree_model_get(model, &iter, 0, &active, 3, &pal, -1); if (active) plist = g_slist_append(plist, pal); } while (gtk_tree_model_iter_next(model, &iter)); return plist; } } // namespace iptux iptux-0.7.4/src/iptux/DialogGroup.h000066400000000000000000000047101323207530100172160ustar00rootroot00000000000000// // C++ Interface: DialogGroup // // Description: // 与多人对话 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DIALOGGROUP_H #define IPTUX_DIALOGGROUP_H #include "iptux/DialogBase.h" #include "iptux/IptuxConfig.h" #include "iptux/ProgramData.h" #include "iptux/mess.h" namespace iptux { class DialogGroup : public DialogBase { public: DialogGroup(GroupInfo *grp, IptuxConfig &config, ProgramData &progdt); virtual ~DialogGroup(); static void GroupDialogEntry(IptuxConfig &config, GroupInfo *grpinf, ProgramData &progdt); virtual void UpdatePalData(PalInfo *pal); virtual void InsertPalData(PalInfo *pal); virtual void DelPalData(PalInfo *pal); virtual void ClearAllPalData(); virtual GSList *GetSelPal(); private: IptuxConfig &config; virtual void InitSublayerSpecify(); void ReadUILayout(); void SaveUILayout(); GtkWidget *CreateMainWindow(); GtkWidget *CreateAllArea(); GtkWidget *CreateMenuBar(); GtkWidget *CreateMemberArea(); GtkWidget *CreateInputArea(); GtkWidget *CreateToolMenu(); GtkTreeModel *CreateMemberModel(); void FillMemberModel(GtkTreeModel *model); GtkWidget *CreateMemberTree(GtkTreeModel *model); bool SendTextMsg(); private: void BroadcastEnclosureMsg(GSList *list); void BroadcastTextMsg(const gchar *msg); static GtkWidget *CreatePopupMenu(GtkTreeModel *model); //回调处理部分 private: static gint MemberTreeCompareByNameFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); static gint MemberTreeCompareByIPFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); static void SetMemberTreeSortFunc(GtkWidget *menuitem, GtkTreeModel *model); static void SetMemberTreeSortType(GtkWidget *menuitem, GtkTreeModel *model); static void DragDataReceived(DialogGroup *dlggrp, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time); static gboolean PopupPickMenu(GtkWidget *treeview, GdkEventButton *event); static void MembertreeItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, DialogGroup *self); static void SendMessage(DialogGroup *dlggrp); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/DialogPeer.cpp000066400000000000000000001262101323207530100173500ustar00rootroot00000000000000// // C++ Implementation: DialogPeer // // Description: // // // Author: cwll ,(C) 2012.02 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "DialogPeer.h" #include #include #include "iptux/Command.h" #include "iptux/HelpDialog.h" #include "iptux/RecvFileData.h" #include "iptux/SendFile.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/dialog.h" #include "iptux/global.h" #include "iptux/output.h" #include "iptux/support.h" #include "iptux/utils.h" namespace iptux { /** * 类构造函数. * @param grp 好友群组信息 */ DialogPeer::DialogPeer(IptuxConfig &config, GroupInfo *grp, ProgramData &progdt) : DialogBase(grp, progdt), config(config), torcvsize(0), rcvdsize(0), timerrcv(0) { ReadUILayout(); } /** * 类析构函数. */ DialogPeer::~DialogPeer() { /* 非常重要,必须在窗口析构之前把定时触发事件停止,不然会出现意想不到的情况 */ if (timerrcv > 0) g_source_remove(timerrcv); /*---------------------------------------------------------------*/ WriteUILayout(); } /** * 好友对话框入口. * @param grpinf 好友群组信息 */ void DialogPeer::PeerDialogEntry(IptuxConfig &config, GroupInfo *grpinf, ProgramData &progdt) { DialogPeer *dlgpr; GtkWidget *window, *widget; dlgpr = new DialogPeer(config, grpinf, progdt); window = dlgpr->CreateMainWindow(); gtk_container_add(GTK_CONTAINER(window), dlgpr->CreateAllArea()); gtk_widget_show_all(window); /* 将焦点置于文本输入框 */ widget = GTK_WIDGET(g_datalist_get_data(&dlgpr->widset, "input-textview-widget")); gtk_widget_grab_focus(widget); /* 从消息队列中移除 */ g_cthrd->Lock(); if (g_cthrd->MsglineContainItem(grpinf)) { g_mwin->MakeItemBlinking(grpinf, FALSE); g_cthrd->PopItemFromMsgline(grpinf); } g_cthrd->Unlock(); /* delete dlgpr;//请不要这样做,此类将会在窗口被摧毁后自动释放 */ } /** * 更新好友信息. * @param pal 好友信息 */ void DialogPeer::UpdatePalData(PalInfo *pal) { GtkWidget *textview; GtkTextBuffer *buffer; GtkTextIter start, end; textview = GTK_WIDGET(g_datalist_get_data(&widset, "info-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(textview)); gtk_text_buffer_get_bounds(buffer, &start, &end); gtk_text_buffer_delete(buffer, &start, &end); FillPalInfoToBuffer(buffer, pal); } /** * 插入好友数据. * @param pal 好友信息 */ void DialogPeer::InsertPalData(PalInfo *pal) { //此函数暂且无须实现 } /** * 删除好友数据. * @param pal 好友信息 */ void DialogPeer::DelPalData(PalInfo *pal) { //此函数暂且无须实现 } /** * 清除本群组所有好友数据. */ void DialogPeer::ClearAllPalData() { //此函数暂且无须实现 } /** * 读取对话框的UI布局数据. */ void DialogPeer::ReadUILayout() { g_datalist_set_data(&dtset, "window-width", GINT_TO_POINTER(config.GetInt("peer_window_width", 570))); g_datalist_set_data( &dtset, "window-height", GINT_TO_POINTER(config.GetInt("peer_window_height", 420))); g_datalist_set_data( &dtset, "main-paned-divide", GINT_TO_POINTER(config.GetInt("peer_main_paned_divide", 375))); g_datalist_set_data( &dtset, "historyinput-paned-divide", GINT_TO_POINTER(config.GetInt("peer_historyinput_paned_divide", 255))); g_datalist_set_data( &dtset, "infoenclosure-paned-divide", GINT_TO_POINTER(config.GetInt("peer_infoenclosure_paned_divide", 255))); g_datalist_set_data( &dtset, "enclosure-paned-divide", GINT_TO_POINTER(config.GetInt("peer_enclosure_paned_divide", 280))); g_datalist_set_data( &dtset, "file-receive-paned-divide", GINT_TO_POINTER(config.GetInt("peer_file_recieve_paned_divide", 140))); } /** * 保存对话框的UI布局数据. */ void DialogPeer::WriteUILayout() { config.SetInt("peer_window_width", GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-width"))); config.SetInt("peer_window_height", GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-height"))); config.SetInt("peer_main_paned_divide", GPOINTER_TO_INT(g_datalist_get_data( &dtset, "main-paned-divide"))); config.SetInt("peer_historyinput_paned_divide", GPOINTER_TO_INT( g_datalist_get_data(&dtset, "historyinput-paned-divide"))); config.SetInt("peer_infoenclosure_paned_divide", GPOINTER_TO_INT( g_datalist_get_data(&dtset, "infoenclosure-paned-divide"))); config.SetInt( "peer_enclosure_paned_divide", GPOINTER_TO_INT(g_datalist_get_data(&dtset, "enclosure-paned-divide"))); config.SetInt("peer_file_recieve_paned_divide", GPOINTER_TO_INT( g_datalist_get_data(&dtset, "file-receive-paned-divide"))); config.Save(); } /** * 创建主窗口. * @return 窗口 */ GtkWidget *DialogPeer::CreateMainWindow() { char buf[MAX_BUFLEN]; GtkWidget *window; gint width, height; PalInfo *palinfor; char ipstr[INET_ADDRSTRLEN]; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); palinfor = (PalInfo *)grpinf->member->data; inet_ntop(AF_INET, &palinfor->ipv4, ipstr, INET_ADDRSTRLEN); snprintf(buf, MAX_BUFLEN, _("Talk with %s(%s) IP:%s"), palinfor->name, palinfor->host, ipstr); gtk_window_set_title(GTK_WINDOW(window), buf); width = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-width")); height = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "window-height")); gtk_window_set_default_size(GTK_WINDOW(window), width, height); gtk_window_set_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER); gtk_window_add_accel_group(GTK_WINDOW(window), accel); widget_enable_dnd_uri(window); g_datalist_set_data(&widset, "window-widget", window); grpinf->dialog = window; g_object_set_data(G_OBJECT(window), "dialog", this); MainWindowSignalSetup(window); g_signal_connect_swapped(GTK_WIDGET(window), "show", G_CALLBACK(ShowDialogPeer), this); return window; } /** * 创建所有区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateAllArea() { GtkWidget *box; GtkWidget *hpaned, *vpaned; gint position; box = gtk_vbox_new(FALSE, 0); /* 加入菜单条 */ gtk_box_pack_start(GTK_BOX(box), CreateMenuBar(), FALSE, FALSE, 0); /* 加入主区域 */ hpaned = gtk_hpaned_new(); g_datalist_set_data(&widset, "main-paned", hpaned); g_object_set_data(G_OBJECT(hpaned), "position-name", (gpointer) "main-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "main-paned-divide")); gtk_paned_set_position(GTK_PANED(hpaned), position); gtk_box_pack_start(GTK_BOX(box), hpaned, TRUE, TRUE, 0); g_signal_connect(hpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); /*/* 加入聊天历史记录&输入区域 */ vpaned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "historyinput-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "historyinput-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); gtk_paned_pack1(GTK_PANED(hpaned), vpaned, TRUE, TRUE); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_paned_pack1(GTK_PANED(vpaned), CreateHistoryArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(vpaned), CreateInputArea(), FALSE, TRUE); /* 加入好友信息&附件区域 */ vpaned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "infoenclosure-paned-divide"); position = GPOINTER_TO_INT( g_datalist_get_data(&dtset, "infoenclosure-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); gtk_paned_pack2(GTK_PANED(hpaned), vpaned, FALSE, TRUE); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_paned_pack1(GTK_PANED(vpaned), CreateInfoArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(vpaned), CreateFileArea(), FALSE, TRUE); return box; } /** * 创建菜单条. * @return 菜单条 */ GtkWidget *DialogPeer::CreateMenuBar() { GtkWidget *menubar; menubar = gtk_menu_bar_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateFileMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateToolMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateHelpMenu()); return menubar; } /** * 创建好友信息区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateInfoArea() { GtkWidget *frame, *sw; GtkWidget *widget; GtkTextBuffer *buffer; frame = gtk_frame_new(_("Info.")); g_datalist_set_data(&widset, "info-frame", frame); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_container_add(GTK_CONTAINER(frame), sw); buffer = gtk_text_buffer_new(progdt.table); if (grpinf->member) FillPalInfoToBuffer(buffer, (PalInfo *)grpinf->member->data); widget = gtk_text_view_new_with_buffer(buffer); gtk_text_view_set_cursor_visible(GTK_TEXT_VIEW(widget), FALSE); gtk_text_view_set_editable(GTK_TEXT_VIEW(widget), FALSE); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(widget), GTK_WRAP_NONE); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "info-textview-widget", widget); return frame; } /** * 创建文件菜单. * @return 菜单 */ GtkWidget *DialogPeer::CreateFileMenu() { GtkWidget *menushell, *window; GtkWidget *menu, *menuitem; window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); menushell = gtk_menu_item_new_with_mnemonic(_("_File")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_menu_item_new_with_label(_("Attach File")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AttachRegular), this); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_S, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_menu_item_new_with_label(_("Attach Folder")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AttachFolder), this); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_D, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_menu_item_new_with_label(_("Request Shared Resources")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AskSharedFiles), grpinf); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_R, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_tearoff_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_menu_item_new_with_label(_("Close")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(gtk_widget_destroy), window); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_W, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); g_datalist_set_data(&widset, "file-menu", menu); return menushell; } /** * 创建工具菜单. * @return 菜单 */ GtkWidget *DialogPeer::CreateToolMenu() { GtkWidget *menushell; GtkWidget *menu, *menuitem; menushell = gtk_menu_item_new_with_mnemonic(_("_Tools")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_menu_item_new_with_label(_("Insert Picture")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(InsertPicture), this); menuitem = gtk_menu_item_new_with_label(_("Clear Buffer")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ClearHistoryBuffer), this); return menushell; } /** * 将好友信息数据写入指定的缓冲区. * @param buffer text-buffer * @param pal class PalInfo */ void DialogPeer::FillPalInfoToBuffer(GtkTextBuffer *buffer, PalInfo *pal) { char buf[MAX_BUFLEN], ipstr[INET_ADDRSTRLEN]; GdkPixbuf *pixbuf; GtkTextIter iter; gtk_text_buffer_get_end_iter(buffer, &iter); snprintf(buf, MAX_BUFLEN, _("Version: %s\n"), pal->version); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (pal->group && *pal->group != '\0') snprintf(buf, MAX_BUFLEN, _("Nickname: %s@%s\n"), pal->name, pal->group); else snprintf(buf, MAX_BUFLEN, _("Nickname: %s\n"), pal->name); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("User: %s\n"), pal->user); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("Host: %s\n"), pal->host); gtk_text_buffer_insert(buffer, &iter, buf, -1); inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); if (pal->segdes && *pal->segdes != '\0') snprintf(buf, MAX_BUFLEN, _("Address: %s(%s)\n"), pal->segdes, ipstr); else snprintf(buf, MAX_BUFLEN, _("Address: %s\n"), ipstr); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (!FLAG_ISSET(pal->flags, 0)) snprintf(buf, MAX_BUFLEN, "%s", _("Compatibility: Microsoft\n")); else snprintf(buf, MAX_BUFLEN, "%s", _("Compatibility: GNU/Linux\n")); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("System coding: %s\n"), pal->encode); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (pal->sign && *pal->sign != '\0') { gtk_text_buffer_insert(buffer, &iter, _("Signature:\n"), -1); gtk_text_buffer_insert_with_tags_by_name(buffer, &iter, pal->sign, -1, "sign-words", NULL); } if (pal->photo && *pal->photo != '\0' && (pixbuf = gdk_pixbuf_new_from_file(pal->photo, NULL))) { gtk_text_buffer_insert(buffer, &iter, _("\nPhoto:\n"), -1); // TODO 缩放多少才合适 pixbuf_shrink_scale_1(&pixbuf, 200, -1); gtk_text_buffer_insert_pixbuf(buffer, &iter, pixbuf); g_object_unref(pixbuf); } } /** * 发送附件给好友 */ void DialogPeer::BroadcastEnclosureMsg(GSList *list) { SendFile sfile; GSList *plist; /* 向选中的成员发送附件 */ plist = NULL; plist = g_slist_append(plist, grpinf->member->data); sfile.BcstFileInfoEntry(plist, list); g_slist_free(plist); } /** * 发送文本消息. * @return 是否发送数据 */ bool DialogPeer::SendTextMsg() { static uint32_t count = 0; GtkWidget *textview; GtkTextBuffer *buffer; GtkTextIter start, end, piter, iter; GdkPixbuf *pixbuf; char buf[MAX_UDPLEN]; gchar *chipmsg, *ptr; pthread_t pid; size_t len; MsgPara *para; ChipData *chip; GSList *dtlist; /* 考察缓冲区内是否存在数据 */ textview = GTK_WIDGET(g_datalist_get_data(&widset, "input-textview-widget")); gtk_widget_grab_focus(textview); //为下一次任务做准备 buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(textview)); gtk_text_buffer_get_bounds(buffer, &start, &end); if (gtk_text_iter_equal(&start, &end)) return false; /* 一些初始化工作 */ buf[0] = '\0'; //缓冲区数据为空 ptr = buf; len = 0; dtlist = NULL; //数据链表为空 /* 获取数据 */ piter = iter = start; //让指针指向缓冲区开始位置 do { /** * @note 由于gtk_text_iter_forward_find_char()会跳过当前字符, * 所以必须先考察第一个字符是否为图片. */ if ((pixbuf = gtk_text_iter_get_pixbuf(&iter))) { /* 读取图片之前的字符数据,并写入缓冲区 */ chipmsg = gtk_text_buffer_get_text(buffer, &piter, &iter, FALSE); snprintf(ptr, MAX_UDPLEN - len, "%s%c", chipmsg, OCCUPY_OBJECT); len += strlen(ptr); ptr = buf + len; g_free(chipmsg); piter = iter; //移动 piter 到新位置 /* 保存图片 */ chipmsg = g_strdup_printf("%s" IPTUX_PATH "/%" PRIx32, g_get_user_config_dir(), count++); gdk_pixbuf_save(pixbuf, chipmsg, "bmp", NULL, NULL); /* 新建一个碎片数据(图片),并加入数据链表 */ chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_PICTURE; chip->data = chipmsg; dtlist = g_slist_append(dtlist, chip); } } while (gtk_text_iter_forward_find_char( &iter, GtkTextCharPredicate(giter_compare_foreach), GUINT_TO_POINTER(ATOM_OBJECT), &end)); /* 读取余下的字符数据,并写入缓冲区 */ chipmsg = gtk_text_buffer_get_text(buffer, &piter, &end, FALSE); snprintf(ptr, MAX_UDPLEN - len, "%s", chipmsg); g_free(chipmsg); /* 新建一个碎片数据(字符串),并加入数据链表 */ chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_STRING; chip->data = g_strdup(buf); dtlist = g_slist_prepend(dtlist, chip); //保证字符串先被发送 /* 清空缓冲区并发送数据 */ gtk_text_buffer_delete(buffer, &start, &end); FeedbackMsg(dtlist); para = PackageMsg(dtlist); pthread_create(&pid, NULL, ThreadFunc(ThreadSendTextMsg), para); pthread_detach(pid); /* g_slist_foreach(dtlist, GFunc(glist_delete_foreach), CHIP_DATA); */ /* g_slist_free(dtlist); */ return true; } /** * 回馈消息. * @param dtlist 数据链表 * @note 请不要修改链表(dtlist)中的数据 */ void DialogPeer::FeedbackMsg(const GSList *dtlist) { MsgPara para; /* 构建消息封装包 */ if (grpinf->member) para.pal = (PalInfo *)grpinf->member->data; else para.pal = g_cthrd->GetPalFromList(grpinf->grpid); para.stype = MESSAGE_SOURCE_TYPE_SELF; para.btype = grpinf->type; para.dtlist = (GSList *)dtlist; /* 交给某人处理吧 */ g_cthrd->InsertMsgToGroupInfoItem(grpinf, ¶); para.dtlist = NULL; //防止参数数据被修改 } /** * 封装消息. * @param dtlist 数据链表 * @return 消息封装包 */ MsgPara *DialogPeer::PackageMsg(GSList *dtlist) { MsgPara *para; para = new MsgPara; if (!(grpinf->member)) para->pal = g_cthrd->GetPalFromList(grpinf->grpid); else para->pal = (PalInfo *)grpinf->member->data; para->stype = MESSAGE_SOURCE_TYPE_SELF; para->btype = grpinf->type; para->dtlist = dtlist; return para; } /** * 图片拖拽事件响应函数. * @param dlgpr 对话框类 * @param context the drag context * @param x where the drop happened * @param y where the drop happened * @param data the received data * @param info the info that has been registered with the target in the * GtkTargetList * @param time the timestamp at which the data was received */ void DialogPeer::DragPicReceived(DialogPeer *dlgpr, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time) { GtkWidget *widget; GtkTextBuffer *buffer; GtkTextIter iter; GdkPixbuf *pixbuf; GSList *list, *flist, *tlist; gint position; if (!ValidateDragData(data, context, time)) { return; } /* 获取(text-buffer)的当前插入点 */ widget = GTK_WIDGET(g_datalist_get_data(&dlgpr->widset, "input-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); g_object_get(buffer, "cursor-position", &position, NULL); gtk_text_buffer_get_iter_at_offset(buffer, &iter, position); /* 分离图片文件和常规文件,图片立即处理,常规文件稍候再处理 */ flist = NULL; //预置常规文件链表为空 tlist = list = selection_data_get_path(data); //获取所有文件 while (tlist) { if ((pixbuf = gdk_pixbuf_new_from_file((char *)tlist->data, NULL))) { /* 既然是图片,那就立即处理吧 */ gtk_text_buffer_insert_pixbuf(buffer, &iter, pixbuf); g_object_unref(pixbuf); } else { /* 将文件路径转移至文件链表(flist) */ flist = g_slist_append(flist, tlist->data); tlist->data = NULL; } tlist = g_slist_next(tlist); } /*/* 释放链表数据 */ g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); /* 如果文件链表有文件,那就添加为附件吧 */ if (flist) { dlgpr->AttachEnclosure(flist); g_slist_foreach(flist, GFunc(g_free), NULL); g_slist_free(flist); widget = GTK_WIDGET( g_datalist_get_data(&dlgpr->widset, "enclosure-frame-widget")); gtk_widget_show(widget); } gtk_drag_finish(context, TRUE, FALSE, time); } /** * 请求获取此好友的共享文件. * @param grpinf 好友群组信息 */ void DialogPeer::AskSharedFiles(GroupInfo *grpinf) { Command cmd; PalInfo *pal; if (!(grpinf->member)) pal = g_cthrd->GetPalFromList(grpinf->grpid); else pal = (PalInfo *)grpinf->member->data; cmd.SendAskShared(g_cthrd->UdpSockQuote(), pal, 0, NULL); } /** * 插入图片到输入缓冲区. * @param dlgpr 对话框类 */ void DialogPeer::InsertPicture(DialogPeer *dlgpr) { GtkWidget *widget, *window; GtkTextBuffer *buffer; GtkTextIter iter; GdkPixbuf *pixbuf; gchar *filename; gint position; window = GTK_WIDGET(g_datalist_get_data(&dlgpr->widset, "window-widget")); if (!(filename = choose_file_with_preview( _("Please select a picture to insert the buffer"), window))) return; if (!(pixbuf = gdk_pixbuf_new_from_file(filename, NULL))) { g_free(filename); return; } g_free(filename); widget = GTK_WIDGET(g_datalist_get_data(&dlgpr->widset, "input-textview-widget")); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); g_object_get(buffer, "cursor-position", &position, NULL); gtk_text_buffer_get_iter_at_offset(buffer, &iter, position); gtk_text_buffer_insert_pixbuf(buffer, &iter, pixbuf); g_object_unref(pixbuf); } /** * 发送文本消息. * @param para 消息参数 */ void DialogPeer::ThreadSendTextMsg(MsgPara *para) { Command cmd; GSList *tlist; char *ptr; int sock; tlist = para->dtlist; while (tlist) { ptr = ((ChipData *)tlist->data)->data; switch (((ChipData *)tlist->data)->type) { case MESSAGE_CONTENT_TYPE_STRING: /* 文本类型 */ cmd.SendMessage(g_cthrd->UdpSockQuote(), para->pal, ptr); break; case MESSAGE_CONTENT_TYPE_PICTURE: /* 图片类型 */ if ((sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) { pop_error(_("Fatal Error!!\nFailed to create new socket!" "\n%s"), strerror(errno)); exit(1); } cmd.SendSublayer(sock, para->pal, IPTUX_MSGPICOPT, ptr); close(sock); //关闭网络套接口 /*/* 删除此图片 */ unlink(ptr); //此文件已无用处 break; default: break; } tlist = g_slist_next(tlist); } /* 释放资源 */ delete para; } /** * 创建文件接收和发送区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateFileArea() { GtkWidget *frame, *vpaned; gint position; frame = gtk_frame_new(_("Enclosure.")); g_datalist_set_data(&widset, "file-enclosure-frame-widget", frame); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); vpaned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "enclosure-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "enclosure-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_container_add(GTK_CONTAINER(frame), vpaned); gtk_paned_pack1(GTK_PANED(vpaned), CreateFileReceiveArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(vpaned), CreateFileSendArea(), FALSE, TRUE); return frame; } /** * 创建文件接收区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateFileReceiveArea() { GtkWidget *vpaned; gint position; vpaned = gtk_vpaned_new(); g_datalist_set_data(&widset, "file-receive-paned-widget", vpaned); g_object_set_data(G_OBJECT(vpaned), "position-name", (gpointer) "file-receive-paned-divide"); position = GPOINTER_TO_INT(g_datalist_get_data(&dtset, "file-receive-paned-divide")); gtk_paned_set_position(GTK_PANED(vpaned), position); g_signal_connect(vpaned, "notify::position", G_CALLBACK(PanedDivideChanged), &dtset); gtk_paned_pack1(GTK_PANED(vpaned), CreateFileToReceiveArea(), TRUE, FALSE); gtk_paned_pack2(GTK_PANED(vpaned), CreateFileReceivedArea(), TRUE, FALSE); return vpaned; } /** * 创建待接收文件区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateFileToReceiveArea() { GtkWidget *frame, *hbox, *vbox, *button, *pbar, *sw, *treeview; GtkTreeModel *model; frame = gtk_frame_new(_("File to be receive.")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); pbar = gtk_progress_bar_new(); g_datalist_set_data(&widset, "file-receive-progress-bar-widget", pbar); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), _("Receiving progress.")); hbox = gtk_hbox_new(FALSE, 1); gtk_box_pack_start(GTK_BOX(hbox), pbar, TRUE, TRUE, 0); button = gtk_button_new_with_label(_("Accept")); g_signal_connect_swapped(button, "clicked", G_CALLBACK(onAcceptButtonClicked), this); g_datalist_set_data(&widset, "file-receive-accept-button", button); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, TRUE, 0); button = gtk_button_new_with_label(_("Refuse")); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, TRUE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(RemoveSelectedRcv), this); g_datalist_set_data(&widset, "file-receive-refuse-button", button); button = gtk_button_new_with_label(_("Detail")); gtk_box_pack_end(GTK_BOX(hbox), button, FALSE, TRUE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(OpenTransDlg), NULL); vbox = gtk_vbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); model = CreateFileToReceiveModel(); g_datalist_set_data_full(&mdlset, "file-to-receive-model", model, GDestroyNotify(g_object_unref)); treeview = CreateFileToReceiveTree(model); g_datalist_set_data(&widset, "file-to-receive-treeview-widget", treeview); g_object_set_data(G_OBJECT(treeview), "dialog", this); gtk_container_add(GTK_CONTAINER(sw), treeview); gtk_box_pack_end(GTK_BOX(vbox), sw, TRUE, TRUE, 0); gtk_container_add(GTK_CONTAINER(frame), vbox); return frame; } /** * 创建已接收文件区域. * @return 主窗体 */ GtkWidget *DialogPeer::CreateFileReceivedArea() { GtkWidget *frame, *sw, *treeview; GtkTreeModel *model; frame = gtk_frame_new(_("File received.")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); model = CreateFileReceivedModel(); g_datalist_set_data_full(&mdlset, "file-received-model", model, GDestroyNotify(g_object_unref)); treeview = CreateFileReceivedTree(model); g_datalist_set_data(&widset, "file-received-treeview-widget", treeview); g_object_set_data(G_OBJECT(treeview), "dialog", this); gtk_container_add(GTK_CONTAINER(sw), treeview); gtk_container_add(GTK_CONTAINER(frame), sw); return frame; } /** * 创建待接收文件树(FileToReceive-tree). * @param model FileToReceive-model * @return 待接收文件树 */ GtkWidget *DialogPeer::CreateFileToReceiveTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeSelection *selection; GtkCellRenderer *cell; GtkTreeViewColumn *column; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE); cell = gtk_cell_renderer_pixbuf_new(); column = gtk_tree_view_column_new_with_attributes("", cell, "pixbuf", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Source"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); g_object_set(cell, "editable", TRUE, NULL); column = gtk_tree_view_column_new_with_attributes(_("SaveAs"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Size"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect_swapped(GTK_WIDGET(view), "button_press_event", G_CALLBACK(RcvTreePopup), view); return view; } /** * 创建待接收文件树底层数据结构. * @return FileToReceive-model */ GtkTreeModel *DialogPeer::CreateFileToReceiveModel() { GtkListStore *model; model = gtk_list_store_new(6, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER); return GTK_TREE_MODEL(model); } /** * 创建已接收文件树(FileReceived-tree). * @param model FileReceived-model * @return 已接收文件树 */ GtkWidget *DialogPeer::CreateFileReceivedTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeSelection *selection; GtkCellRenderer *cell; GtkTreeViewColumn *column; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_SINGLE); cell = gtk_cell_renderer_pixbuf_new(); column = gtk_tree_view_column_new_with_attributes("", cell, "pixbuf", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Source"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Name"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Size"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect_swapped(GTK_WIDGET(view), "button_press_event", G_CALLBACK(RcvTreePopup), view); return view; } /** * 创建已接收文件树底层数据结构. * @return FileReceived-model */ GtkTreeModel *DialogPeer::CreateFileReceivedModel() { GtkListStore *model; model = gtk_list_store_new(6, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER); return GTK_TREE_MODEL(model); } /** * 显示信息/文件接收UI(是否显示信息或文件接收). * */ void DialogPeer::ShowInfoEnclosure(DialogPeer *dlgpr) { PalInfo *palinfor; GtkTreeModel *mdltorcv, *mdlrcvd, *mdltmp; GSList *ecslist; GtkWidget *widget, *hpaned, *pbar; float progress = 0.0; GdkPixbuf *pixbuf, *rpixbuf, *dpixbuf; FileInfo *file; gchar *filesize, *path; char progresstip[MAX_BUFLEN]; GtkTreeIter iter; gint receiving; //标记是不是窗口在正传送文件时被关闭,又打开的。 receiving = 0; /* 获取文件图标 */ rpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_FILE); dpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_DIRECTORY); //设置界面显示 palinfor = (PalInfo *)(dlgpr->grpinf->member->data); mdltorcv = (GtkTreeModel *)g_datalist_get_data(&(dlgpr->mdlset), "file-to-receive-model"); gtk_list_store_clear(GTK_LIST_STORE(mdltorcv)); mdlrcvd = (GtkTreeModel *)g_datalist_get_data(&(dlgpr->mdlset), "file-received-model"); gtk_list_store_clear(GTK_LIST_STORE(mdlrcvd)); ecslist = g_cthrd->GetPalEnclosure(palinfor); if (ecslist) { //只要有该好友的接收文件信息(不分待接收和未接收),就显示 hpaned = GTK_WIDGET(g_datalist_get_data(&(dlgpr->widset), "main-paned")); widget = GTK_WIDGET(g_datalist_get_data(&(dlgpr->widset), "info-frame")); gtk_widget_hide(widget); widget = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-enclosure-frame-widget")); gtk_paned_pack2(GTK_PANED(hpaned), widget, FALSE, TRUE); widget = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-paned-widget")); gtk_widget_show(widget); //将从中心节点取到的数据向附件接收列表填充 dlgpr->torcvsize = 0; while (ecslist) { file = (FileInfo *)ecslist->data; filesize = numeric_to_size(file->filesize); switch (GET_MODE(file->fileattr)) { case IPMSG_FILE_REGULAR: pixbuf = rpixbuf; break; case IPMSG_FILE_DIR: pixbuf = dpixbuf; break; default: pixbuf = NULL; break; } if (file->finishedsize < file->filesize) { file->filepath = ipmsg_get_filename_me(file->filepath, &path); if (file->finishedsize > 0) receiving += 1; mdltmp = mdltorcv; dlgpr->torcvsize += file->filesize; } else mdltmp = mdlrcvd; gtk_list_store_append(GTK_LIST_STORE(mdltmp), &iter); gtk_list_store_set(GTK_LIST_STORE(mdltmp), &iter, 0, pixbuf, 1, file->fileown->name, 2, file->filepath, 3, filesize, 5, file, -1); g_free(filesize); ecslist = g_slist_next(ecslist); } g_slist_free(ecslist); //设置进度条,如果接收完成重新载入待接收和已接收列表 if (dlgpr->torcvsize == 0) { progress = 0; snprintf(progresstip, MAX_BUFLEN, "%s", _("Receiving Progress.")); } else { if (dlgpr->rcvdsize == 0) snprintf(progresstip, MAX_BUFLEN, _("%s to Receive."), numeric_to_size(dlgpr->torcvsize)); else { progress = percent(dlgpr->rcvdsize, dlgpr->torcvsize) / 100; snprintf(progresstip, MAX_BUFLEN, _("%s Of %s Received."), numeric_to_size(dlgpr->rcvdsize), numeric_to_size(dlgpr->torcvsize)); } } if (progress == 1.0) { g_source_remove(dlgpr->timerrcv); snprintf(progresstip, MAX_BUFLEN, "%s", _("Mission Completed!")); } pbar = GTK_WIDGET(g_datalist_get_data(&(dlgpr->widset), "file-receive-progress-bar-widget")); gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(pbar), progress); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), progresstip); } else { widget = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-paned-widget")); gtk_widget_hide(widget); } /* 释放文件图标 */ if (rpixbuf) g_object_unref(rpixbuf); if (dpixbuf) g_object_unref(dpixbuf); if (receiving > 0) dlgpr->onAcceptButtonClicked(dlgpr); } /** * 显示窗口事件响应函数. *@param dlgpr 对话框类 * */ bool DialogPeer::UpdataEnclosureRcvUI(DialogPeer *dlgpr) { GtkTreeModel *model; GtkWidget *pbar, *button; float progress = 0.0; FileInfo *file; GtkTreeIter iter; GtkIconTheme *theme; GdkPixbuf *pixbuf; const char *statusfile; char progresstip[MAX_BUFLEN]; /* 获取文件图标 */ theme = gtk_icon_theme_get_default(); statusfile = "tip-finish"; pixbuf = gtk_icon_theme_load_icon(theme, statusfile, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); //处理待接收文件界面显示 model = (GtkTreeModel *)g_datalist_get_data(&(dlgpr->mdlset), "file-to-receive-model"); if (!model) { g_source_remove(dlgpr->timerrcv); return FALSE; } dlgpr->rcvdsize = 0; gtk_tree_model_get_iter_first(model, &iter); do { //遍历待接收model gtk_tree_model_get(model, &iter, 5, &file, -1); if (pixbuf && (file->finishedsize == file->filesize)) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, -1); dlgpr->rcvdsize += file->finishedsize; } while (gtk_tree_model_iter_next(model, &iter)); //设置进度条,如果接收完成重新载入待接收和已接收列表 if (dlgpr->torcvsize == 0) { progress = 0; snprintf(progresstip, MAX_BUFLEN, "%s", _("Receiving Progress.")); } else { if (dlgpr->rcvdsize == 0) snprintf(progresstip, MAX_BUFLEN, _("%s to Receive."), numeric_to_size(dlgpr->torcvsize)); else { progress = percent(dlgpr->rcvdsize, dlgpr->torcvsize) / 100; snprintf(progresstip, MAX_BUFLEN, _("%s Of %s Received."), numeric_to_size(dlgpr->rcvdsize), numeric_to_size(dlgpr->torcvsize)); } } pbar = GTK_WIDGET(g_datalist_get_data(&(dlgpr->widset), "file-receive-progress-bar-widget")); gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(pbar), progress); gtk_progress_bar_set_text(GTK_PROGRESS_BAR(pbar), progresstip); if ((progress == 1) || (progress == 0)) { if (progress == 1) { g_source_remove(dlgpr->timerrcv); dlgpr->ShowInfoEnclosure(dlgpr); } //只要不是在接收过程中,恢复接收和拒收按键 button = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-accept-button")); gtk_widget_set_sensitive(button, TRUE); button = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-refuse-button")); gtk_widget_set_sensitive(button, TRUE); } else { //接收过程中,禁止点接收和拒收按键 button = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-accept-button")); gtk_widget_set_sensitive(button, FALSE); button = GTK_WIDGET( g_datalist_get_data(&(dlgpr->widset), "file-receive-refuse-button")); gtk_widget_set_sensitive(button, FALSE); } return TRUE; } /** * 显示窗口事件响应函数. *@param dlgpr 对话框类 * */ void DialogPeer::ShowDialogPeer(DialogPeer *dlgpr) { //这个事件有可能需要触发其它功能,暂没有直接用ShowInfoEnclosure来执行 ShowInfoEnclosure(dlgpr); } /** * 接收文件函数. *@param dlgpr 对话框类 * */ void DialogPeer::onAcceptButtonClicked(DialogPeer *self) { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; gchar *filename; FileInfo *file; pthread_t pid; const gchar *filepath = pop_save_path(GTK_WIDGET(self->grpinf->dialog)); self->progdt.path = filepath; /* 考察数据集中是否存在项 */ widget = GTK_WIDGET( g_datalist_get_data(&(self->widset), "file-to-receive-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (!model) return; if (!gtk_tree_model_get_iter_first(model, &iter)) return; self->torcvsize = 0; /* 将选中的项投入文件数据接收类 */ do { gtk_tree_model_get(model, &iter, 2, &filename, 5, &file, -1); g_free(file->filepath); file->filepath = g_strdup_printf( "%s%s%s", filepath, *(filepath + 1) != '\0' ? "/" : "", filename); pthread_create(&pid, NULL, ThreadFunc(ThreadRecvFile), file); pthread_detach(pid); g_free(filename); self->torcvsize += file->filesize; } while (gtk_tree_model_iter_next(model, &iter)); self->rcvdsize = 0; self->timerrcv = g_timeout_add(300, GSourceFunc(UpdataEnclosureRcvUI), self); } /** * 接收文件数据. * @param file 文件信息 */ void DialogPeer::ThreadRecvFile(FileInfo *file) { RecvFileData rfdt(file); rfdt.RecvFileDataEntry(); } /** * 获取待发送成员列表. * @return plist 获取待发送成员列表 * 调用该函数后须free plist */ GSList *DialogPeer::GetSelPal() { PalInfo *pal; GSList *plist; pal = (PalInfo *)(grpinf->member->data); plist = NULL; plist = g_slist_append(plist, pal); return plist; } /** *从接收文件的TreeView删除选定行(待接收和已接收都用此函数). * @param widget TreeView */ void DialogPeer::RemoveSelectedRcv(GtkWidget *widget) { GtkTreeModel *model; GtkTreeSelection *TreeSel; GtkTreeIter iter; FileInfo *file; DialogPeer *dlg; GList *list; dlg = (DialogPeer *)(g_object_get_data(G_OBJECT(widget), "dialog")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); //从中心结点删除 TreeSel = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); list = gtk_tree_selection_get_selected_rows(TreeSel, NULL); if (!list) return; while (list) { gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &iter, (GtkTreePath *)g_list_nth(list, 0)->data); gtk_tree_model_get(model, &iter, 5, &file, -1); g_cthrd->PopItemFromEnclosureList(file); list = g_list_next(list); } g_list_free(list); //从列表中删除 RemoveSelectedFromTree(widget); //重新刷新窗口显示 dlg->ShowInfoEnclosure(dlg); } /** *显示接收附件的TreeView的弹出菜单回调函数.(待接收和已接收都用此函数) * @param widget TreeView * @param event 事件 */ gint DialogPeer::RcvTreePopup(GtkWidget *treeview, GdkEvent *event) { GtkWidget *menu, *menuitem; GdkEventButton *event_button; menu = gtk_menu_new(); menuitem = gtk_menu_item_new_with_label(_("Remove Selected")); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(RemoveSelectedRcv), treeview); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); if (event->type == GDK_BUTTON_PRESS) { event_button = (GdkEventButton *)event; if (event_button->button == 3) { gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event_button->button, event_button->time); gtk_widget_show(menuitem); return TRUE; } } return FALSE; } } // namespace iptux iptux-0.7.4/src/iptux/DialogPeer.h000066400000000000000000000053071323207530100170200ustar00rootroot00000000000000// // C++ Interface: DialogPeer // // Description: // 与单个好友对话 // // Author: cwll ,(C) 2012.02 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DIALOGPEER_H #define IPTUX_DIALOGPEER_H #include "iptux/DialogBase.h" #include "iptux/IptuxConfig.h" #include "iptux/mess.h" namespace iptux { class DialogPeer : public DialogBase { public: DialogPeer(IptuxConfig &config, GroupInfo *grp, ProgramData &progdt); virtual ~DialogPeer(); static void PeerDialogEntry(IptuxConfig &config, GroupInfo *grpinf, ProgramData &progdt); virtual void UpdatePalData(PalInfo *pal); virtual void InsertPalData(PalInfo *pal); virtual void DelPalData(PalInfo *pal); virtual void ClearAllPalData(); virtual GSList *GetSelPal(); static void ShowDialogPeer(DialogPeer *dlgpr); private: void ReadUILayout(); void WriteUILayout(); GtkWidget *CreateMainWindow(); GtkWidget *CreateAllArea(); GtkWidget *CreateMenuBar(); GtkWidget *CreateInfoArea(); GtkWidget *CreateFileArea(); GtkWidget *CreateFileReceiveArea(); GtkWidget *CreateFileToReceiveArea(); GtkWidget *CreateFileReceivedArea(); GtkWidget *CreateFileToReceiveTree(GtkTreeModel *model); GtkTreeModel *CreateFileToReceiveModel(); GtkWidget *CreateFileReceivedTree(GtkTreeModel *model); GtkTreeModel *CreateFileReceivedModel(); GtkWidget *CreateFileMenu(); GtkWidget *CreateToolMenu(); void FillPalInfoToBuffer(GtkTextBuffer *buffer, PalInfo *pal); private: void BroadcastEnclosureMsg(GSList *list); bool SendTextMsg(); void FeedbackMsg(const GSList *dtlist); MsgPara *PackageMsg(GSList *dtlist); //回调处理部分 private: static void DragPicReceived(DialogPeer *dlgpr, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time); static void AskSharedFiles(GroupInfo *grpinf); static void InsertPicture(DialogPeer *dlgpr); static void DialogPeerDestroy(DialogPeer *dlgpr); static void onAcceptButtonClicked(DialogPeer *dlgpr); static void ThreadRecvFile(FileInfo *file); static void ShowInfoEnclosure(DialogPeer *dlgpr); static bool UpdataEnclosureRcvUI(DialogPeer *dlgpr); static void RemoveSelectedRcv(GtkWidget *widget); static gint RcvTreePopup(GtkWidget *treeview, GdkEvent *event); //线程处理 private: static void ThreadSendTextMsg(MsgPara *para); protected: IptuxConfig &config; int64_t torcvsize; //总计待接收大小(包括已接收) int64_t rcvdsize; //总计已接收大小 guint timerrcv; //接收文件界面更新计时器ID }; } // namespace iptux #endif iptux-0.7.4/src/iptux/HelpDialog.cpp000066400000000000000000000136331323207530100173510ustar00rootroot00000000000000// // C++ Implementation: HelpDialog // // Description: // // // Author: Jally , (C) 2008 // Jally & ManPT , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "HelpDialog.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/support.h" namespace iptux { /* 静态变量初始化 */ GtkWidget *HelpDialog::about = NULL; GtkWidget *HelpDialog::more = NULL; HelpDialog::HelpDialog() {} HelpDialog::~HelpDialog() {} /** * 关于对话框入口. */ void HelpDialog::AboutEntry() { HelpDialog hlp; if (!about) { about = hlp.CreateAboutDialog(); hlp.RunHelpDialog(&about); } else gtk_window_present(GTK_WINDOW(about)); } /** * 更多信息对话框入口. */ void HelpDialog::MoreEntry() { HelpDialog hlp; if (!more) { more = hlp.CreateMoreDialog(); hlp.RunHelpDialog(&more); } else gtk_window_present(GTK_WINDOW(more)); } /** * 创建关于对话框. */ GtkWidget *HelpDialog::CreateAboutDialog() { const char *authors[] = {_("Jally "), _("ManPT "), NULL}; const char *artists[] = {_("Jally "), _("LiWeijian "), _("ManPT "), NULL}; const char *translators = _("alick \n" "ManPT "); GtkWidget *dialog; dialog = gtk_about_dialog_new(); gtk_about_dialog_set_program_name(GTK_ABOUT_DIALOG(dialog), _("iptux")); gtk_about_dialog_set_version(GTK_ABOUT_DIALOG(dialog), VERSION); gtk_about_dialog_set_copyright(GTK_ABOUT_DIALOG(dialog), "Copyright © 2008-2009 by Jally"); gtk_about_dialog_set_comments(GTK_ABOUT_DIALOG(dialog), _("A GTK+ based LAN Messenger.")); gtk_about_dialog_set_website(GTK_ABOUT_DIALOG(dialog), "https://github.com/iptux-src/iptux"); gtk_about_dialog_set_license(GTK_ABOUT_DIALOG(dialog), "GPL 2+"); gtk_about_dialog_set_authors(GTK_ABOUT_DIALOG(dialog), authors); gtk_about_dialog_set_artists(GTK_ABOUT_DIALOG(dialog), artists); gtk_about_dialog_set_translator_credits(GTK_ABOUT_DIALOG(dialog), translators); gtk_about_dialog_set_logo_icon_name(GTK_ABOUT_DIALOG(dialog), "iptux"); return dialog; } /** * 创建更多信息对话框. */ GtkWidget *HelpDialog::CreateMoreDialog() { char *labels[] = {_("Help"), _("Contributors"), _("..."), NULL}; char *text[] = { _("Project Home: \nhttps://github.com/iptux-src/iptux\n\n" "User and Developer Group: \nhttps://groups.google.com/group/iptux/\n\n" "Note that you can get help form the project wiki page.\n\n" "If you find no solutions in any of the existed documents, " "feel free to drop a email at iptux@googlegroups.com, " "lots of users and developers would be glade to help about your " "problems."), _("It's an honor that iptux was contributed voluntarilly by many people. " "Without your help, iptux could never make it.\n\n" "Especially, Here's some we would like to thank much:\n\n" "ChenGang\n" "\n" "\n" "\n" "\n" "\n" "..."), _("...")}; GtkWidget *dialog; GtkWidget *frame, *sw; GtkWidget *notebook, *label, *view; GtkTextBuffer *buffer; gint page; dialog = gtk_dialog_new_with_buttons(_("More About Iptux"), NULL, GtkDialogFlags(0), GTK_STOCK_CLOSE, GTK_RESPONSE_CLOSE, NULL); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); gtk_widget_set_size_request(dialog, 500, 350); frame = gtk_frame_new(NULL); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), frame, TRUE, TRUE, 0); gtk_container_set_border_width(GTK_CONTAINER(frame), 3); notebook = gtk_notebook_new(); gtk_container_add(GTK_CONTAINER(frame), notebook); page = 0; while (labels[page]) { sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); label = gtk_label_new(labels[page]); gtk_notebook_append_page(GTK_NOTEBOOK(notebook), sw, label); view = gtk_text_view_new(); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(view), GTK_WRAP_WORD); gtk_container_add(GTK_CONTAINER(sw), view); gtk_text_view_set_cursor_visible(GTK_TEXT_VIEW(view), FALSE); gtk_text_view_set_indent(GTK_TEXT_VIEW(view), 20); gtk_text_view_set_pixels_inside_wrap(GTK_TEXT_VIEW(view), 5); gtk_text_view_set_editable(GTK_TEXT_VIEW(view), FALSE); buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(view)); gtk_text_buffer_set_text(buffer, text[page], -1); page++; } return dialog; } /** * 运行对话框. * @param dialog 对话框指针 */ void HelpDialog::RunHelpDialog(GtkWidget **dialog) { g_signal_connect(*dialog, "close", G_CALLBACK(gtk_widget_destroy), NULL); g_signal_connect(*dialog, "response", G_CALLBACK(gtk_widget_destroy), NULL); g_signal_connect_swapped(*dialog, "destroy", G_CALLBACK(DialogDestroy), dialog); gtk_window_set_skip_taskbar_hint(GTK_WINDOW(*dialog), TRUE); gtk_window_set_skip_pager_hint(GTK_WINDOW(*dialog), TRUE); gtk_widget_show_all(*dialog); } /** * 对话框被摧毁的响应函数. * @param dialog 对话框指针 */ void HelpDialog::DialogDestroy(GtkWidget **dialog) { *dialog = NULL; } } // namespace iptux iptux-0.7.4/src/iptux/HelpDialog.h000066400000000000000000000013041323207530100170060ustar00rootroot00000000000000// // C++ Interface: HelpDialog // // Description: // 创建帮助相关对话框 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_HELP_DIALOG_H #define IPTUX_HELP_DIALOG_H #include namespace iptux { class HelpDialog { public: HelpDialog(); ~HelpDialog(); static void AboutEntry(); static void MoreEntry(); private: GtkWidget *CreateAboutDialog(); GtkWidget *CreateMoreDialog(); void RunHelpDialog(GtkWidget **dialog); static GtkWidget *about; static GtkWidget *more; //回调处理部分 private: static void DialogDestroy(GtkWidget **dialog); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/IptuxConfig.cpp000066400000000000000000000066371323207530100176060ustar00rootroot00000000000000#include "IptuxConfig.h" #include #include #include #include #include using namespace std; namespace iptux { IptuxConfig::IptuxConfig(string& fname) : fname(fname) { ifstream ifs(fname.c_str()); if (!ifs.is_open()) { g_warning("config file %s not found", fname.c_str()); return; } Json::CharReaderBuilder rbuilder; std::string errs; bool ok = Json::parseFromStream(rbuilder, ifs, &root, &errs); if (!ok) { g_warning("invalid content in config file %s:\n%s", fname.c_str(), errs.c_str()); return; } int version = root.get("version", 1).asInt(); if (version != 1) { g_error("unknown config file version %d (from %s)", version, fname.c_str()); return; } } IptuxConfig::~IptuxConfig() {} int IptuxConfig::GetInt(const string& key) const { return GetInt(key, 0); } int IptuxConfig::GetInt(const string& key, int defaultValue) const { return root.get(key, defaultValue).asInt(); } void IptuxConfig::SetInt(const string& key, int value) { root[key] = value; } bool IptuxConfig::GetBool(const string& key) const { return root.get(key, false).asBool(); } void IptuxConfig::SetBool(const string& key, bool value) { root[key] = value; } string IptuxConfig::GetString(const string& key) const { return GetString(key, ""); } string IptuxConfig::GetString(const string& key, const string& defaultValue) const { return root.get(key, defaultValue).asString(); } void IptuxConfig::SetString(const string& key, const string& value) { root[key] = value; } double IptuxConfig::GetDouble(const string& key) const { return root.get(key, 0.0).asDouble(); } void IptuxConfig::SetDouble(const string& key, double value) { root[key] = value; } vector IptuxConfig::GetStringList(const string& key) const { vector res; Json::Value value = root[key]; if (value.isNull()) { return res; } if (value.isArray()) { for (size_t i = 0; i < value.size(); ++i) { res.push_back(value.get(i, "").asString()); } } return res; } void IptuxConfig::SetStringList(const string& key, const vector& value) { root[key] = Json::arrayValue; for (size_t i = 0; i < value.size(); ++i) { root[key][int(i)] = value[i]; } } void IptuxConfig::SetVector(const string& key, const vector& value) { root[key] = Json::arrayValue; for (size_t i = 0; i < value.size(); ++i) { root[key][int(i)] = value[i]; } } vector IptuxConfig::GetVector(const string& key) const { vector res; Json::Value value = root[key]; if (value.isNull()) { return res; } if (value.isArray()) { for (size_t i = 0; i < value.size(); ++i) { res.push_back(value[int(i)]); } } return res; } IptuxConfig& IptuxConfig::Save() { if (!g_file_test(fname.c_str(), G_FILE_TEST_IS_REGULAR)) { const char* dirname = g_path_get_dirname(fname.c_str()); if (g_mkdir_with_parents(dirname, 0700) != 0) { g_error("create config dir %s failed: %s", dirname, strerror(errno)); } } root["version"] = 1; ofstream ofs(fname.c_str()); if (!ofs) { g_warning("open config file %s for write failed.", fname.c_str()); return *this; } ofs << root; if (!ofs) { g_warning("write to config file %s failed.", fname.c_str()); } return *this; } } // namespace iptux iptux-0.7.4/src/iptux/IptuxConfig.h000066400000000000000000000025741323207530100172470ustar00rootroot00000000000000#ifndef IPTUX_IPTUX_CONFIG_H #define IPTUX_IPTUX_CONFIG_H #include #include #include namespace iptux { class IptuxConfig { public: explicit IptuxConfig(std::string& fname); ~IptuxConfig(); int GetInt(const std::string& key) const; int GetInt(const std::string& key, int defaultValue) const; void SetInt(const std::string& key, int value); std::string GetString(const std::string& key) const; std::string GetString(const std::string& key, const std::string& defaultValue) const; void SetString(const std::string& key, const std::string& value); bool GetBool(const std::string& key) const; bool GetBool(const std::string& key, bool defaultValue) const; void SetBool(const std::string& key, bool value); double GetDouble(const std::string& key) const; double GetDouble(const std::string& key, double defaultValue) const; void SetDouble(const std::string& key, double value); std::vector GetStringList(const std::string& key) const; void SetStringList(const std::string& key, const std::vector& value); std::vector GetVector(const std::string& key) const; void SetVector(const std::string& key, const std::vector& value); IptuxConfig& Save(); private: std::string fname; Json::Value root; }; } // namespace iptux #endif iptux-0.7.4/src/iptux/IptuxConfigTest.cpp000066400000000000000000000012121323207530100204260ustar00rootroot00000000000000#include #include #include "gtest/gtest.h" #include "iptux/IptuxConfig.h" using namespace std; using namespace iptux; TEST(IptuxConfig, SetStringList) { char templateFname[] = "/tmp/iptuxXXXXXX.json"; char* tmpfile = mktemp(templateFname); string fname(tmpfile); IptuxConfig config(fname); config.SetStringList("key", vector()); EXPECT_EQ(config.GetStringList("key").size(), 0); config.SetStringList("key", vector{"hello", "world!"}); EXPECT_EQ(config.GetStringList("key").size(), 2); config.SetStringList("key", vector{"hello"}); EXPECT_EQ(config.GetStringList("key").size(), 1); } iptux-0.7.4/src/iptux/LogSystem.cpp000066400000000000000000000046411323207530100172660ustar00rootroot00000000000000// // C++ Implementation: LogSystem // // Description: // 实时写入日志信息 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "LogSystem.h" #include #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/ipmsg.h" #include "iptux/utils.h" #define LOG_START_HEADER "=====================================" #define LOG_END_HEADER "-------------------------------------" namespace iptux { LogSystem::LogSystem() : fdc(-1), fds(-1) {} LogSystem::~LogSystem() { close(fdc); close(fds); } void LogSystem::InitSublayer() { const gchar *env; char path[MAX_PATHLEN]; env = g_get_user_config_dir(); snprintf(path, MAX_PATHLEN, "%s" LOG_PATH "/communicate.log", env); fdc = open(path, O_WRONLY | O_CREAT | O_APPEND, 0644); snprintf(path, MAX_PATHLEN, "%s" LOG_PATH "/system.log", env); fds = open(path, O_WRONLY | O_CREAT | O_APPEND, 0644); } void LogSystem::CommunicateLog(MsgPara *msgpara, const char *fmt, ...) { gchar *log, *msg, *ptr; va_list ap; if (!g_progdt->IsSaveChatHistory()) { return; } PalInfo *pal = msgpara->pal; if (msgpara->stype == MESSAGE_SOURCE_TYPE_PAL) ptr = getformattime(TRUE, _("Recevied-From: Nickname:%s User:%s Host:%s"), pal->name, pal->user, pal->host); else if (msgpara->stype == MESSAGE_SOURCE_TYPE_SELF) { if (msgpara->pal) ptr = getformattime(TRUE, _("Send-To: Nickname:%s User:%s Host:%s"), pal->name, pal->user, pal->host); else ptr = getformattime(TRUE, _("Send-Broadcast")); } else return; va_start(ap, fmt); msg = g_strdup_vprintf(fmt, ap); va_end(ap); log = g_strdup_printf("%s\n%s\n%s\n%s\n\n", LOG_START_HEADER, ptr, msg, LOG_END_HEADER); write(fdc, log, strlen(log)); g_free(log); g_free(ptr); g_free(msg); } void LogSystem::SystemLog(const char *fmt, ...) { gchar *log, *msg, *ptr; va_list ap; if (!g_progdt->IsSaveChatHistory()) { return; } ptr = getformattime(TRUE, _("User:%s Host:%s"), g_get_user_name(), g_get_host_name()); va_start(ap, fmt); msg = g_strdup_vprintf(fmt, ap); va_end(ap); log = g_strdup_printf("%s\n%s\n%s\n%s\n\n", LOG_START_HEADER, ptr, msg, LOG_END_HEADER); g_free(ptr); g_free(msg); write(fds, log, strlen(log)); g_free(log); } } // namespace iptuxiptux-0.7.4/src/iptux/LogSystem.h000066400000000000000000000010301323207530100167200ustar00rootroot00000000000000// // C++ Interface: LogSystem // // Description: // 相关日志记录 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_LOGSYSTEM_H #define IPTUX_LOGSYSTEM_H #include "iptux/mess.h" namespace iptux { class LogSystem { public: LogSystem(); ~LogSystem(); void InitSublayer(); void CommunicateLog(MsgPara *msgpara, const char *fmt, ...); void SystemLog(const char *fmt, ...); private: int fdc, fds; }; } // namespace iptux #endif iptux-0.7.4/src/iptux/MainWindow.cpp000066400000000000000000002565531323207530100174270ustar00rootroot00000000000000// // C++ Implementation: MainWindow // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "MainWindow.h" #include #include #include "iptux/Command.h" #include "iptux/DataSettings.h" #include "iptux/DetectPal.h" #include "iptux/DialogGroup.h" #include "iptux/DialogPeer.h" #include "iptux/HelpDialog.h" #include "iptux/RevisePal.h" #include "iptux/ShareFile.h" #include "iptux/StatusIcon.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/support.h" #include "iptux/utils.h" namespace iptux { static const int TRANS_TREE_MAX = 14; /** * 类构造函数. */ MainWindow::MainWindow(IptuxConfig &config, ProgramData &progdt) : config(config), progdt(progdt), widset(NULL), mdlset(NULL), tmdllist(NULL), accel(NULL), timerid(0), windowConfig(250, 510, "main_window") { windowConfig.LoadFromConfig(config); } /** * 类析构函数. */ MainWindow::~MainWindow() { ClearSublayer(); } /** * 创建程序主窗口入口. */ void MainWindow::CreateWindow() { GtkWidget *window; GtkWidget *widget; InitSublayer(); /* 创建主窗口 */ window = CreateMainWindow(); gtk_container_add(GTK_CONTAINER(window), CreateAllArea()); gtk_widget_show_all(window); /* 聚焦到好友树(paltree)区域 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "paltree-treeview-widget")); gtk_widget_grab_focus(widget); /* 隐藏好友清单 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "pallist-box-widget")); gtk_widget_hide(widget); if (progdt.IsAutoHidePanelAfterLogin()) { gtk_widget_hide(window); } /* 创建传输窗口 */ window = CreateTransWindow(); gtk_container_add(GTK_CONTAINER(window), CreateTransArea()); gtk_widget_show_all(window); gtk_widget_hide(window); } /** * 更改窗口显示模式. */ void MainWindow::AlterWindowMode() { GtkWidget *window; window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); if (gtk_widget_get_visible(window)) { gtk_widget_hide(window); } else { gtk_widget_show(window); } } /** * 获取主窗口指针. * @return 主窗口 */ GtkWidget *MainWindow::ObtainWindow() { return GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); } /** * 好友树(paltree)中是否已经包含此IP地址的好友信息数据. * @param ipv4 ipv4 * @return 是否包含 */ bool MainWindow::PaltreeContainItem(in_addr_t ipv4) { GtkTreeModel *model; GtkTreeIter iter; GroupInfo *grpinf; PalInfo *pal; bool exist; if (!(pal = g_cthrd->GetPalFromList(ipv4)) || !(grpinf = g_cthrd->GetPalRegularItem(pal))) return false; model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); exist = GroupGetPaltreeItem(model, &iter, grpinf); return exist; } /** * 更新此IP地址好友在好友树(paltree)中的信息数据. * @param ipv4 ipv4 */ void MainWindow::UpdateItemToPaltree(in_addr_t ipv4) { GtkTreeModel *model; GtkTreeIter parent, iter; GroupInfo *pgrpinf, *grpinf; PalInfo *pal; if (!(pal = g_cthrd->GetPalFromList(ipv4)) || !(grpinf = g_cthrd->GetPalRegularItem(pal))) return; /* 更新常规模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &iter, grpinf); /* 更新网段模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); pgrpinf = g_cthrd->GetPalSegmentItem(pal); GroupGetPaltreeItem(model, &iter, pgrpinf); GroupGetPaltreeItemWithParent(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &iter, grpinf); /* 更新分组模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); pgrpinf = g_cthrd->GetPalGroupItem(pal); GroupGetPrevPaltreeItem(model, &iter, grpinf); gtk_tree_model_iter_parent(model, &parent, &iter); if (gtk_tree_model_iter_n_children(model, &parent) == 1) gtk_tree_store_remove(GTK_TREE_STORE(model), &parent); else gtk_tree_store_remove(GTK_TREE_STORE(model), &iter); if (!GroupGetPaltreeItem(model, &parent, pgrpinf)) { gtk_tree_store_append(GTK_TREE_STORE(model), &parent, NULL); FillGroupInfoToPaltree(model, &parent, pgrpinf); } gtk_tree_store_append(GTK_TREE_STORE(model), &iter, &parent); FillGroupInfoToPaltree(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); /* 更新广播模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "broadcast-paltree-model")); pgrpinf = g_cthrd->GetPalBroadcastItem(pal); GroupGetPaltreeItem(model, &iter, pgrpinf); GroupGetPaltreeItemWithParent(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &iter, grpinf); } /** * 附加此IP地址的好友到好友树(paltree). * @param ipv4 ipv4 */ void MainWindow::AttachItemToPaltree(in_addr_t ipv4) { GtkTreeModel *model; GtkTreeIter parent, iter; GroupInfo *pgrpinf, *grpinf; PalInfo *pal; if (!(pal = g_cthrd->GetPalFromList(ipv4)) || !(grpinf = g_cthrd->GetPalRegularItem(pal))) return; /* 添加到常规模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); gtk_tree_store_append(GTK_TREE_STORE(model), &iter, NULL); FillGroupInfoToPaltree(model, &iter, grpinf); /* 添加到网段模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); pgrpinf = g_cthrd->GetPalSegmentItem(pal); if (!GroupGetPaltreeItem(model, &parent, pgrpinf)) { gtk_tree_store_append(GTK_TREE_STORE(model), &parent, NULL); FillGroupInfoToPaltree(model, &parent, pgrpinf); } gtk_tree_store_append(GTK_TREE_STORE(model), &iter, &parent); FillGroupInfoToPaltree(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); /* 添加到分组模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); pgrpinf = g_cthrd->GetPalGroupItem(pal); if (!GroupGetPaltreeItem(model, &parent, pgrpinf)) { gtk_tree_store_append(GTK_TREE_STORE(model), &parent, NULL); FillGroupInfoToPaltree(model, &parent, pgrpinf); } gtk_tree_store_append(GTK_TREE_STORE(model), &iter, &parent); FillGroupInfoToPaltree(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); /* 添加到广播模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "broadcast-paltree-model")); pgrpinf = g_cthrd->GetPalBroadcastItem(pal); if (!GroupGetPaltreeItem(model, &parent, pgrpinf)) { gtk_tree_store_append(GTK_TREE_STORE(model), &parent, NULL); FillGroupInfoToPaltree(model, &parent, pgrpinf); } gtk_tree_store_append(GTK_TREE_STORE(model), &iter, &parent); FillGroupInfoToPaltree(model, &iter, grpinf); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); } /** * 从好友树(paltree)中删除此IP地址的好友. * @param ipv4 ipv4 */ void MainWindow::DelItemFromPaltree(in_addr_t ipv4) { GtkTreeModel *model; GtkTreeIter parent, iter; GroupInfo *pgrpinf, *grpinf; PalInfo *pal; if (!(pal = g_cthrd->GetPalFromList(ipv4)) || !(grpinf = g_cthrd->GetPalRegularItem(pal))) return; /* 从常规模式树移除 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); gtk_tree_store_remove(GTK_TREE_STORE(model), &iter); /* 从网段模式树移除 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); pgrpinf = g_cthrd->GetPalSegmentItem(pal); GroupGetPaltreeItem(model, &parent, pgrpinf); if (g_slist_length(pgrpinf->member) != 1) { iter = parent; GroupGetPaltreeItemWithParent(model, &iter, grpinf); gtk_tree_store_remove(GTK_TREE_STORE(model), &iter); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); } else gtk_tree_store_remove(GTK_TREE_STORE(model), &parent); /* 从分组模式树移除 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); pgrpinf = g_cthrd->GetPalGroupItem(pal); GroupGetPaltreeItem(model, &parent, pgrpinf); if (g_slist_length(pgrpinf->member) != 1) { iter = parent; GroupGetPaltreeItemWithParent(model, &iter, grpinf); gtk_tree_store_remove(GTK_TREE_STORE(model), &iter); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); } else gtk_tree_store_remove(GTK_TREE_STORE(model), &parent); /* 从广播模式树移除 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "broadcast-paltree-model")); pgrpinf = g_cthrd->GetPalBroadcastItem(pal); GroupGetPaltreeItem(model, &parent, pgrpinf); if (g_slist_length(pgrpinf->member) != 1) { iter = parent; GroupGetPaltreeItemWithParent(model, &iter, grpinf); gtk_tree_store_remove(GTK_TREE_STORE(model), &iter); UpdateGroupInfoToPaltree(model, &parent, pgrpinf); } else gtk_tree_store_remove(GTK_TREE_STORE(model), &parent); } /** * 从好友树(paltree)中删除所有好友数据. */ void MainWindow::ClearAllItemFromPaltree() { GtkTreeModel *model; model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); gtk_tree_store_clear(GTK_TREE_STORE(model)); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); gtk_tree_store_clear(GTK_TREE_STORE(model)); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); gtk_tree_store_clear(GTK_TREE_STORE(model)); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "broadcast-paltree-model")); gtk_tree_store_clear(GTK_TREE_STORE(model)); } /** * 让指定的项在好友树(paltree)中闪烁. * @param grpinf class GroupInfo * @param blinking 是否继续闪烁 * @note 如果我猜得没错,调用此函数的环境一定已经对(grpinf)加锁了 */ void MainWindow::MakeItemBlinking(GroupInfo *grpinf, bool blinking) { GtkTreeModel *model; GtkTreeIter iter; GroupInfo *pgrpinf; /* 成员为空表明此项已经不存在model中,也就没必要再处理它了 */ if (!grpinf->member) return; /* 闪烁项 */ switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: /* 闪烁常规模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); /* 闪烁网段模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); pgrpinf = g_cthrd->GetPalSegmentItem((PalInfo *)grpinf->member->data); GroupGetPaltreeItem(model, &iter, pgrpinf); GroupGetPaltreeItemWithParent(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); /* 闪烁分组模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); pgrpinf = g_cthrd->GetPalGroupItem((PalInfo *)grpinf->member->data); GroupGetPaltreeItem(model, &iter, pgrpinf); GroupGetPaltreeItemWithParent(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); /* 闪烁广播模式树 */ model = GTK_TREE_MODEL( g_datalist_get_data(&mdlset, "broadcast-paltree-model")); pgrpinf = g_cthrd->GetPalBroadcastItem((PalInfo *)grpinf->member->data); GroupGetPaltreeItem(model, &iter, pgrpinf); GroupGetPaltreeItemWithParent(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); break; case GROUP_BELONG_TYPE_SEGMENT: /* 闪烁网段模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "segment-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); break; case GROUP_BELONG_TYPE_GROUP: /* 闪烁分组模式树 */ model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "group-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); break; case GROUP_BELONG_TYPE_BROADCAST: /* 闪烁广播模式树 */ model = GTK_TREE_MODEL( g_datalist_get_data(&mdlset, "broadcast-paltree-model")); GroupGetPaltreeItem(model, &iter, grpinf); BlinkGroupItemToPaltree(model, &iter, blinking); break; default: break; } } /** * 打开文件传输窗口. */ void MainWindow::OpenTransWindow() { ShowTransWindow(&widset); } /** * 更新文件传输树(trans-tree)的指定项. * @param para 项值 * @note 若项不存在则须自动加入 */ void MainWindow::UpdateItemToTransTree(GData **para) { GtkTreeModel *model; GtkTreeIter iter; gpointer data; /* 查询项所在位置,若不存在则自动加入 */ data = NULL; model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "trans-model")); if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, TRANS_TREE_MAX, &data, -1); if (para == data) break; } while (gtk_tree_model_iter_next(model, &iter)); } if (para != data) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, TRANS_TREE_MAX, para, -1); } /** * @note 鉴于参数值(*para)的原地址有可能会被重用, 所以当("data"==null) * 时应该清空参数指针值,以防止其他后来项误认此项为自己的大本营. */ if (!g_datalist_get_data(para, "data")) gtk_list_store_set(GTK_LIST_STORE(model), &iter, TRANS_TREE_MAX, NULL, -1); /* 重设数据 */ gtk_list_store_set( GTK_LIST_STORE(model), &iter, 0, g_datalist_get_data(para, "status"), 1, g_datalist_get_data(para, "task"), 2, g_datalist_get_data(para, "peer"), 3, g_datalist_get_data(para, "ip"), 4, g_datalist_get_data(para, "filename"), 5, g_datalist_get_data(para, "filelength"), 6, g_datalist_get_data(para, "finishlength"), 7, GPOINTER_TO_INT(g_datalist_get_data(para, "progress")), 8, g_datalist_get_data(para, "pro-text"), 9, g_datalist_get_data(para, "cost"), 10, g_datalist_get_data(para, "remain"), 11, g_datalist_get_data(para, "rate"), 12, g_datalist_get_data(para, "filepath"), 13, g_datalist_get_data(para, "data"), -1); } /** * 查询此刻是否存在活动的文件传输. * @return 活动与否 */ bool MainWindow::TransmissionActive() { GtkTreeModel *model; GtkTreeIter iter; gpointer data; data = NULL; model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "trans-model")); if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, TRANS_TREE_MAX, &data, -1); if (data) break; } while (gtk_tree_model_iter_next(model, &iter)); } return data; } /** * 初始化底层数据. */ void MainWindow::InitSublayer() { GtkTreeModel *model; g_datalist_init(&widset); g_datalist_init(&mdlset); accel = gtk_accel_group_new(); timerid = gdk_threads_add_timeout(1000, GSourceFunc(UpdateUI), this); model = CreatePaltreeModel(); g_datalist_set_data_full(&mdlset, "regular-paltree-model", model, GDestroyNotify(g_object_unref)); tmdllist = g_list_append(tmdllist, model); model = CreatePaltreeModel(); g_datalist_set_data_full(&mdlset, "segment-paltree-model", model, GDestroyNotify(g_object_unref)); tmdllist = g_list_append(tmdllist, model); model = CreatePaltreeModel(); g_datalist_set_data_full(&mdlset, "group-paltree-model", model, GDestroyNotify(g_object_unref)); tmdllist = g_list_append(tmdllist, model); model = CreatePaltreeModel(); g_datalist_set_data_full(&mdlset, "broadcast-paltree-model", model, GDestroyNotify(g_object_unref)); tmdllist = g_list_append(tmdllist, model); model = CreatePallistModel(); g_datalist_set_data_full(&mdlset, "pallist-model", model, GDestroyNotify(g_object_unref)); model = CreateTransModel(); g_datalist_set_data_full(&mdlset, "trans-model", model, GDestroyNotify(g_object_unref)); } /** * 清空底层数据. */ void MainWindow::ClearSublayer() { g_datalist_clear(&widset); g_datalist_clear(&mdlset); g_list_free(tmdllist); if (accel) g_object_unref(accel); if (timerid > 0) g_source_remove(timerid); } /** * 创建主窗口. * @return 主窗口 */ GtkWidget *MainWindow::CreateMainWindow() { GdkGeometry geometry = {50, 200, G_MAXINT, G_MAXINT, 0, 0, 2, 5, 0.0, 0.0, GDK_GRAVITY_NORTH_WEST}; GdkWindowHints hints = GdkWindowHints( GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE | GDK_HINT_BASE_SIZE | /*GDK_HINT_RESIZE_INC |*/ GDK_HINT_WIN_GRAVITY | GDK_HINT_USER_POS | GDK_HINT_USER_SIZE); GtkWidget *window; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), _("iptux")); gtk_window_set_default_size(GTK_WINDOW(window), windowConfig.GetWidth(), windowConfig.GetHeight()); gtk_window_set_geometry_hints(GTK_WINDOW(window), window, &geometry, hints); gtk_window_set_default_icon_name("iptux"); gtk_window_add_accel_group(GTK_WINDOW(window), accel); g_datalist_set_data(&widset, "window-widget", window); g_signal_connect_swapped(window, "delete-event", G_CALLBACK(onDeleteEvent), this); g_signal_connect(window, "configure-event", G_CALLBACK(MWinConfigureEvent), this); return window; } /** * 创建文件传输主窗口. * @return 主窗口 */ GtkWidget *MainWindow::CreateTransWindow() { GtkWidget *window; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), _("Files Transmission Management")); gtk_window_set_default_size(GTK_WINDOW(window), config.GetInt("trans_window_width", 500), config.GetInt("trans_window_height", 350)); gtk_window_set_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER); gtk_container_set_border_width(GTK_CONTAINER(window), 5); g_signal_connect_swapped(window, "delete-event", G_CALLBACK(HideTransWindow), &widset); g_signal_connect(window, "configure-event", G_CALLBACK(TWinConfigureEvent), this); g_datalist_set_data(&widset, "trans-window-widget", window); return window; } /** * 创建所有区域. * @return 主窗体 */ GtkWidget *MainWindow::CreateAllArea() { GtkWidget *box, *paned; box = gtk_vbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), CreateMenuBar(), FALSE, FALSE, 0); gtk_box_pack_start(GTK_BOX(box), CreateToolBar(), FALSE, FALSE, 0); paned = gtk_vpaned_new(); g_object_set_data(G_OBJECT(paned), "position-name", (gpointer) "mwin-main-paned-divide"); gtk_paned_set_position(GTK_PANED(paned), config.GetInt("mwin_main_paned_divide", 210)); gtk_container_set_border_width(GTK_CONTAINER(paned), 4); gtk_box_pack_start(GTK_BOX(box), paned, TRUE, TRUE, 0); g_signal_connect(paned, "notify::position", G_CALLBACK(PanedDivideChanged), this); gtk_paned_pack1(GTK_PANED(paned), CreatePaltreeArea(), TRUE, TRUE); gtk_paned_pack2(GTK_PANED(paned), CreatePallistArea(), FALSE, TRUE); return box; } /** * 创建文件传输窗口其他区域. * @return 主窗体 */ GtkWidget *MainWindow::CreateTransArea() { GtkWidget *box, *hbb; GtkWidget *sw, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(box), sw, TRUE, TRUE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "trans-model")); widget = CreateTransTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "trans-treeview-widget", widget); hbb = gtk_hbutton_box_new(); gtk_button_box_set_layout(GTK_BUTTON_BOX(hbb), GTK_BUTTONBOX_END); gtk_box_pack_start(GTK_BOX(box), hbb, FALSE, FALSE, 0); button = gtk_button_new_from_stock(GTK_STOCK_CLEAR); gtk_box_pack_start(GTK_BOX(hbb), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ClearTransWindow), &widset); return box; } /** * 创建菜单条. * @return 菜单条 */ GtkWidget *MainWindow::CreateMenuBar() { GtkWidget *menubar; menubar = gtk_menu_bar_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateFileMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateToolMenu()); gtk_menu_shell_append(GTK_MENU_SHELL(menubar), CreateHelpMenu()); return menubar; } /** * 创建工具条. * @return 工具条 */ GtkWidget *MainWindow::CreateToolBar() { GtkWidget *toolbar; GtkToolItem *toolitem; GtkWidget *widget; toolbar = gtk_toolbar_new(); g_object_set(toolbar, "icon-size", 1, NULL); gtk_toolbar_set_style(GTK_TOOLBAR(toolbar), GTK_TOOLBAR_ICONS); toolitem = gtk_tool_button_new_from_stock(GTK_STOCK_GO_BACK); gtk_toolbar_insert(GTK_TOOLBAR(toolbar), toolitem, -1); g_signal_connect_swapped(toolitem, "clicked", G_CALLBACK(GoPrevTreeModel), this); toolitem = gtk_tool_item_new(); gtk_tool_item_set_expand(toolitem, TRUE); gtk_toolbar_insert(GTK_TOOLBAR(toolbar), toolitem, -1); widget = gtk_label_new(_("Pals Online: 0")); gtk_container_add(GTK_CONTAINER(toolitem), widget); g_datalist_set_data(&widset, "online-label-widget", widget); toolitem = gtk_tool_button_new_from_stock(GTK_STOCK_GO_FORWARD); gtk_toolbar_insert(GTK_TOOLBAR(toolbar), toolitem, -1); g_signal_connect_swapped(toolitem, "clicked", G_CALLBACK(GoNextTreeModel), this); return toolbar; } /** * 创建好友树区域. * @return 主窗体 */ GtkWidget *MainWindow::CreatePaltreeArea() { GtkWidget *sw; GtkWidget *widget; GtkTreeModel *model; sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "regular-paltree-model")); widget = CreatePaltreeTree(model); g_object_set_data(G_OBJECT(widget), "paltree-model", model); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "paltree-treeview-widget", widget); return sw; } /** * 创建好友清单区域. * @return 主窗体 */ GtkWidget *MainWindow::CreatePallistArea() { GtkWidget *box, *hbox; GtkWidget *sw, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); g_datalist_set_data(&widset, "pallist-box-widget", box); /* 创建好友清单部分 */ sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(box), sw, TRUE, TRUE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "pallist-model")); widget = CreatePallistTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "pallist-treeview-widget", widget); /* 创建接受搜索输入部分 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); /*/* 关闭按钮 */ button = gtk_button_new(); widget = gtk_image_new_from_stock(GTK_STOCK_CLOSE, GTK_ICON_SIZE_BUTTON); gtk_button_set_image(GTK_BUTTON(button), widget); g_object_set(button, "relief", GTK_RELIEF_NONE, NULL); gtk_widget_set_size_request(button, -1, 1); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(HidePallistArea), &widset); /*/* 输入框 */ widget = gtk_entry_new(); gtk_entry_set_activates_default(GTK_ENTRY(widget), TRUE); gtk_entry_set_icon_from_stock(GTK_ENTRY(widget), GTK_ENTRY_ICON_SECONDARY, GTK_STOCK_FIND); gtk_widget_add_events(widget, GDK_KEY_PRESS_MASK); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Search Pals")); g_signal_connect(widget, "key-press-event", G_CALLBACK(ClearPallistEntry), NULL); g_signal_connect(widget, "changed", G_CALLBACK(PallistEntryChanged), &widset); g_datalist_set_data(&widset, "pallist-entry-widget", widget); return box; } /** * 创建文件菜单. * @return 菜单 */ GtkWidget *MainWindow::CreateFileMenu() { GtkWidget *menushell, *window; GtkWidget *menu, *menuitem; GtkWidget *image; menushell = gtk_menu_item_new_with_mnemonic(_("_File")); window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Detect")); image = gtk_image_new_from_icon_name("menu-detect", GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(DetectPal::DetectEntry), window); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_D, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Find")); image = gtk_image_new_from_stock(GTK_STOCK_FIND, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ShowPallistArea), &widset); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_F, GDK_CONTROL_MASK, GTK_ACCEL_VISIBLE); menuitem = gtk_separator_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Quit")); image = gtk_image_new_from_stock(GTK_STOCK_QUIT, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect(menuitem, "activate", G_CALLBACK(iptux_gui_quit), NULL); return menushell; } /** * 创建工具菜单. * @return 菜单 */ GtkWidget *MainWindow::CreateToolMenu() { GtkWidget *menushell, *window; GtkWidget *menu, *submenu, *menuitem; GtkWidget *image; window = GTK_WIDGET(g_datalist_get_data(&widset, "window-widget")); menushell = gtk_menu_item_new_with_mnemonic(_("_Tools")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); /* 参数设置 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Preferences")); image = gtk_image_new_from_stock(GTK_STOCK_PREFERENCES, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(DataSettings::ResetDataEntry), window); /* 文件传输 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Transmission")); image = gtk_image_new_from_stock(GTK_STOCK_CONNECT, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ShowTransWindow), &widset); /* 文件共享 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Shared Management")); image = gtk_image_new_from_icon_name("menu-share", GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ShareFile::ShareEntry), window); /* 群组成员排序 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Sort")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); submenu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menuitem), submenu); /*/* 按昵称排序 */ NO_OPERATION_C menuitem = gtk_radio_menu_item_new_with_label(NULL, _("By Nickname")); g_object_set_data(G_OBJECT(menuitem), "compare-func", (gpointer)PaltreeCompareByNameFunc); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetPaltreeSortFunc), &mdlset); /*/* 按IP地址排序 */ menuitem = gtk_radio_menu_item_new_with_label_from_widget( GTK_RADIO_MENU_ITEM(menuitem), _("By IP")); g_object_set_data(G_OBJECT(menuitem), "compare-func", (gpointer)PaltreeCompareByIPFunc); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetPaltreeSortFunc), &mdlset); /*/* 分割符 */ menuitem = gtk_separator_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); /*/* 升序 */ NO_OPERATION_C menuitem = gtk_radio_menu_item_new_with_label(NULL, _("Ascending")); g_object_set_data(G_OBJECT(menuitem), "sort-type", GINT_TO_POINTER(GTK_SORT_ASCENDING)); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetPaltreeSortType), &mdlset); /*/* 降序 */ menuitem = gtk_radio_menu_item_new_with_label_from_widget( GTK_RADIO_MENU_ITEM(menuitem), _("Descending")); g_object_set_data(G_OBJECT(menuitem), "sort-type", GINT_TO_POINTER(GTK_SORT_DESCENDING)); gtk_menu_shell_append(GTK_MENU_SHELL(submenu), menuitem); g_signal_connect(menuitem, "toggled", G_CALLBACK(SetPaltreeSortType), &mdlset); /* 更新成员 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Update")); image = gtk_image_new_from_stock(GTK_STOCK_REFRESH, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(UpdatePalTree), this); gtk_widget_add_accelerator(menuitem, "activate", accel, GDK_KEY_F5, GdkModifierType(0), GTK_ACCEL_VISIBLE); return menushell; } /** * 创建帮助菜单. * @return 菜单 */ GtkWidget *MainWindow::CreateHelpMenu() { const char *faq = _("http://code.google.com/p/iptux/wiki/FAQ?wl=en"); GtkWidget *menushell; GtkWidget *menu, *menuitem; menushell = gtk_menu_item_new_with_mnemonic(_("_Help")); menu = gtk_menu_new(); gtk_menu_item_set_submenu(GTK_MENU_ITEM(menushell), menu); menuitem = gtk_image_menu_item_new_from_stock(GTK_STOCK_ABOUT, accel); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect(menuitem, "activate", G_CALLBACK(HelpDialog::AboutEntry), NULL); menuitem = gtk_image_menu_item_new_with_mnemonic(_("_More")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect(menuitem, "activate", G_CALLBACK(HelpDialog::MoreEntry), NULL); menuitem = gtk_image_menu_item_new_with_mnemonic(_("_FAQ")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(iptux_open_url), (gpointer)faq); return menushell; } /** * 好友树(paltree)底层数据结构. * 7,0 closed-expander,1 open-expander,2 info.,3 extras,4 style,5 color,6 data * \n 关闭的展开器;打开的展开器;群组信息;扩展信息;字体风格;字体颜色;群组数据 \n * @return paltree-model */ GtkTreeModel *MainWindow::CreatePaltreeModel() { GtkTreeStore *model; model = gtk_tree_store_new(7, GDK_TYPE_PIXBUF, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, PANGO_TYPE_ATTR_LIST, GDK_TYPE_COLOR, G_TYPE_POINTER); gtk_tree_sortable_set_default_sort_func( GTK_TREE_SORTABLE(model), GtkTreeIterCompareFunc(PaltreeCompareByNameFunc), NULL, NULL); gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); return GTK_TREE_MODEL(model); } /** * 好友清单(pallist)底层数据结构. * 7,0 icon,1 name,2 group,3 ipstr,4 user,5 host,6 data \n * 好友头像;好友昵称;好友群组;IP地址串;好友用户;好友主机;好友数据 \n * @return pallist-model * @note 鉴于好友清单(pallist)常年保持隐藏状态,所以请不要有事没事就往 * 此model中填充数据,好友清单也无须与好友最新状态保持同步. */ GtkTreeModel *MainWindow::CreatePallistModel() { GtkListStore *model; model = gtk_list_store_new(7, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER); return GTK_TREE_MODEL(model); } /** * 文件传输树(trans-tree)底层数据结构. * 14,0 status,1 task,2 peer,3 ip,4 filename,5 filelength,6 finishlength,7 * progress, 8 pro-text,9 cost,10 remain,11 rate,12,pathname,13 data,14 para \n * 任务状态;任务类型;任务对端;文件名(如果当前是文件夹,该项指正在传输的文件夹内单个文件, * 整个文件夹传输完成后,该项指向当前是文件夹);文件长度;完成长度;完成进度; * 进度串;已花费时间;任务剩余时间;传输速度;带路径文件名(不显示);文件传输类;参数指针值 * \n * @return trans-model */ GtkTreeModel *MainWindow::CreateTransModel() { GtkListStore *model; model = gtk_list_store_new(15, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_INT, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER, G_TYPE_POINTER); return GTK_TREE_MODEL(model); } /** * 创建好友树(paltree). * @param model paltree-model * @return 好友树 */ GtkWidget *MainWindow::CreatePaltreeTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeSelection *selection; GtkTreeViewColumn *column; GtkCellRenderer *cell; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_level_indentation(GTK_TREE_VIEW(view), 10); gtk_tree_view_set_show_expanders(GTK_TREE_VIEW(view), FALSE); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), FALSE); widget_enable_dnd_uri(view); g_object_set(view, "has-tooltip", TRUE, NULL); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(GTK_TREE_SELECTION(selection), GTK_SELECTION_NONE); column = gtk_tree_view_column_new(); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_object_set_data(G_OBJECT(view), "info-column", column); /* 展开器区域 */ cell = gtk_cell_renderer_pixbuf_new(); g_object_set(cell, "follow-state", TRUE, NULL); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(GTK_TREE_VIEW_COLUMN(column), cell, "pixbuf", 0, "pixbuf-expander-closed", 0, "pixbuf-expander-open", 1, NULL); g_object_set_data(G_OBJECT(column), "expander-cell", cell); /* 群组信息区域 */ cell = gtk_cell_renderer_text_new(); g_object_set(cell, "xalign", 0.0, "wrap-mode", PANGO_WRAP_WORD, NULL); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(GTK_TREE_VIEW_COLUMN(column), cell, "text", 2, "attributes", 4, "foreground-gdk", 5, NULL); /* 扩展信息区域 */ cell = gtk_cell_renderer_text_new(); g_object_set(cell, "xalign", 0.0, "wrap-mode", PANGO_WRAP_WORD, NULL); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(GTK_TREE_VIEW_COLUMN(column), cell, "text", 3, "attributes", 4, "foreground-gdk", 5, NULL); /* 连接信号 */ g_signal_connect(view, "query-tooltip", G_CALLBACK(PaltreeQueryTooltip), this); g_signal_connect(view, "row-activated", G_CALLBACK(onPaltreeItemActivated), this); g_signal_connect(view, "drag-data-received", G_CALLBACK(PaltreeDragDataReceived), this); g_signal_connect(view, "button-press-event", G_CALLBACK(PaltreePopupMenu), NULL); g_signal_connect(view, "button-release-event", G_CALLBACK(PaltreeChangeStatus), NULL); return view; } /** * 创建好友清单(pallist). * @param model pallist-model * @return 好友清单 */ GtkWidget *MainWindow::CreatePallistTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeViewColumn *column; GtkCellRenderer *cell; GtkTreeSelection *selection; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); gtk_tree_view_set_rules_hint(GTK_TREE_VIEW(view), TRUE); widget_enable_dnd_uri(view); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(GTK_TREE_SELECTION(selection), GTK_SELECTION_NONE); column = gtk_tree_view_column_new(); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_column_set_title(column, _("Nickname")); cell = gtk_cell_renderer_pixbuf_new(); g_object_set(cell, "follow-state", TRUE, NULL); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "pixbuf", 0, NULL); cell = gtk_cell_renderer_text_new(); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "text", 1, NULL); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Group"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("IPv4"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("User"), cell, "text", 4, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Host"), cell, "text", 5, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); g_signal_connect(view, "row-activated", G_CALLBACK(PallistItemActivated), this); g_signal_connect(view, "drag-data-received", G_CALLBACK(PallistDragDataReceived), this); return view; } /** * 创建文件传输树(trans-tree). * @param model trans-model * @return 传输树 */ GtkWidget *MainWindow::CreateTransTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeViewColumn *column; GtkCellRenderer *cell; GtkTreeSelection *selection; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); gtk_tree_view_set_rules_hint(GTK_TREE_VIEW(view), TRUE); gtk_tree_view_set_rubber_banding(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE); g_signal_connect(view, "button-press-event", G_CALLBACK(TransPopupMenu), NULL); cell = gtk_cell_renderer_pixbuf_new(); column = gtk_tree_view_column_new_with_attributes(_("State"), cell, "pixbuf", 0, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Task"), cell, "text", 1, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Peer"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("IPv4"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Filename"), cell, "text", 4, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Size"), cell, "text", 5, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Completed"), cell, "text", 6, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_progress_new(); column = gtk_tree_view_column_new_with_attributes( _("Progress"), cell, "value", 7, "text", 8, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Cost"), cell, "text", 9, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Remaining"), cell, "text", 10, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Rate"), cell, "text", 11, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); return view; } /** * 获取项(grpinf)在数据集(model)中的当前位置. * @param model model * @param iter 位置由此返回 * @param grpinf class GroupInfo * @return 是否查找成功 */ bool MainWindow::GroupGetPrevPaltreeItem(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf) { GroupInfo *pgrpinf; GtkTreeIter parent; if (!gtk_tree_model_get_iter_first(model, &parent)) return false; do { gtk_tree_model_get(model, &parent, 6, &pgrpinf, -1); if (pgrpinf->grpid == grpinf->grpid) { *iter = parent; break; } if (!gtk_tree_model_iter_children(model, iter, &parent)) continue; do { gtk_tree_model_get(model, iter, 6, &pgrpinf, -1); if (pgrpinf->grpid == grpinf->grpid) break; } while (gtk_tree_model_iter_next(model, iter)); if (pgrpinf->grpid == grpinf->grpid) break; } while (gtk_tree_model_iter_next(model, &parent)); return (pgrpinf->grpid == grpinf->grpid); } /** * 获取项(grpinf)在数据集(model)中的位置. * @param model model * @param iter 位置由此返回 * @param grpinf class GroupInfo * @return 是否查找成功 */ bool MainWindow::GroupGetPaltreeItem(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf) { GroupInfo *pgrpinf; if (!gtk_tree_model_get_iter_first(model, iter)) return false; do { gtk_tree_model_get(model, iter, 6, &pgrpinf, -1); if (pgrpinf->grpid == grpinf->grpid) break; } while (gtk_tree_model_iter_next(model, iter)); return (pgrpinf->grpid == grpinf->grpid); } /** * 获取项(grpinf)在数据集(model)中的位置. * @param model model * @param iter 父节点位置/位置由此返回 * @param grpinf class GroupInfo * @return 是否查找成功 */ bool MainWindow::GroupGetPaltreeItemWithParent(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf) { GtkTreeIter parent; GroupInfo *pgrpinf; parent = *iter; if (!gtk_tree_model_iter_children(model, iter, &parent)) return false; do { gtk_tree_model_get(model, iter, 6, &pgrpinf, -1); if (pgrpinf->grpid == grpinf->grpid) break; } while (gtk_tree_model_iter_next(model, iter)); return (pgrpinf->grpid == grpinf->grpid); } /** * 填充群组数据(grpinf)到数据集(model)指定位置(iter). * @param model model * @param iter iter * @param grpinf class GroupInfo */ void MainWindow::FillGroupInfoToPaltree(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf) { static GdkColor color = {0xff, 0x5252, 0xb8b8, 0x3838}; GtkIconTheme *theme; GdkPixbuf *cpixbuf, *opixbuf; PangoAttrList *attrs; PangoAttribute *attr; PangoFontDescription *dspt; char ipstr[INET_ADDRSTRLEN]; gchar *file, *info, *extra; PalInfo *pal; /* 创建图标 */ theme = gtk_icon_theme_get_default(); if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { pal = (PalInfo *)grpinf->member->data; file = iptux_erase_filename_suffix(pal->iconfile); cpixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); opixbuf = GDK_PIXBUF(g_object_ref(cpixbuf)); g_free(file); } else { cpixbuf = gtk_icon_theme_load_icon(theme, "tip-hide", MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); opixbuf = gtk_icon_theme_load_icon(theme, "tip-show", MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); } /* 创建主信息 */ if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { pal = (PalInfo *)grpinf->member->data; inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); info = g_strdup_printf("%s\n%s", pal->name, ipstr); } else info = g_strdup(grpinf->name); /* 创建扩展信息 */ if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) extra = NULL; else extra = g_strdup_printf("(%u)", g_slist_length(grpinf->member)); /* 创建字体风格 */ attrs = pango_attr_list_new(); if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { dspt = pango_font_description_from_string(progdt.font); attr = pango_attr_font_desc_new(dspt); pango_attr_list_insert(attrs, attr); pango_font_description_free(dspt); } else { attr = pango_attr_size_new(8192); pango_attr_list_insert(attrs, attr); attr = pango_attr_style_new(PANGO_STYLE_ITALIC); pango_attr_list_insert(attrs, attr); attr = pango_attr_weight_new(PANGO_WEIGHT_BOLD); pango_attr_list_insert(attrs, attr); } /* 设置相应的数据 */ gtk_tree_store_set(GTK_TREE_STORE(model), iter, 0, cpixbuf, 1, opixbuf, 2, info, 3, extra, 4, attrs, 5, &color, 6, grpinf, -1); /* 释放资源 */ if (cpixbuf) g_object_unref(cpixbuf); if (opixbuf) g_object_unref(opixbuf); g_free(info); g_free(extra); pango_attr_list_unref(attrs); } /** * 更新群组数据(grpinf)到数据集(model)指定位置(iter). * @param model model * @param iter iter * @param grpinf class GroupInfo */ void MainWindow::UpdateGroupInfoToPaltree(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf) { GtkIconTheme *theme; GdkPixbuf *cpixbuf, *opixbuf; PangoAttrList *attrs; PangoAttribute *attr; PangoFontDescription *dspt; char ipstr[INET_ADDRSTRLEN]; gchar *file, *info, *extra; PalInfo *pal; /* 创建图标 */ cpixbuf = opixbuf = NULL; theme = gtk_icon_theme_get_default(); if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { pal = (PalInfo *)grpinf->member->data; file = iptux_erase_filename_suffix(pal->iconfile); cpixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); opixbuf = GDK_PIXBUF(g_object_ref(cpixbuf)); g_free(file); } /* 创建主信息 */ info = NULL; if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { pal = (PalInfo *)grpinf->member->data; inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); info = g_strdup_printf("%s\n%s", pal->name, ipstr); } /* 创建扩展信息 */ extra = NULL; if (grpinf->type != GROUP_BELONG_TYPE_REGULAR) extra = g_strdup_printf("(%u)", g_slist_length(grpinf->member)); /* 创建字体风格 */ attrs = NULL; if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { attrs = pango_attr_list_new(); dspt = pango_font_description_from_string(progdt.font); attr = pango_attr_font_desc_new(dspt); pango_attr_list_insert(attrs, attr); pango_font_description_free(dspt); } /* 设置相应的数据 */ if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) gtk_tree_store_set(GTK_TREE_STORE(model), iter, 0, cpixbuf, 1, opixbuf, 2, info, 4, attrs, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), iter, 3, extra, -1); /* 释放资源 */ if (cpixbuf) g_object_unref(cpixbuf); if (opixbuf) g_object_unref(opixbuf); g_free(info); g_free(extra); if (attrs) pango_attr_list_unref(attrs); } /** * 闪烁指定项. * @param model model * @param iter iter * @param blinking 是否继续闪烁 */ void MainWindow::BlinkGroupItemToPaltree(GtkTreeModel *model, GtkTreeIter *iter, bool blinking) { static GdkColor color1 = {0xff, 0x5252, 0xb8b8, 0x3838}, color2 = {0xff, 0x0000, 0x0000, 0xffff}; GdkColor *color; if (blinking) { gtk_tree_model_get(model, iter, 5, &color, -1); if ((color->red == color1.red) && (color->green == color1.green) && (color->blue == color1.blue)) gtk_tree_store_set(GTK_TREE_STORE(model), iter, 5, &color2, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), iter, 5, &color1, -1); } else gtk_tree_store_set(GTK_TREE_STORE(model), iter, 5, &color1, -1); } /** * 为文件传输树(trans-tree)创建弹出菜单. * @param model trans-model * @return 菜单 */ GtkWidget *MainWindow::CreateTransPopupMenu(GtkTreeModel *model) { GtkWidget *menu, *menuitem; GtkTreePath *path; GtkTreeIter iter; gchar *remaining; gboolean sensitive = TRUE; if (!(path = (GtkTreePath *)(g_object_get_data(G_OBJECT(model), "selected-path")))) return NULL; gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 10, &remaining, -1); if (g_strcmp0(remaining, "")) sensitive = FALSE; menu = gtk_menu_new(); menuitem = gtk_menu_item_new_with_label(_("Open This File")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(OpenThisFile), model); gtk_widget_set_sensitive(GTK_WIDGET(menuitem), sensitive); menuitem = gtk_menu_item_new_with_label(_("Open Containing Folder")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(OpenContainingFolder), model); gtk_widget_set_sensitive(GTK_WIDGET(menuitem), sensitive); menuitem = gtk_menu_item_new_with_label(_("Terminate Task")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(TerminateTransTask), model); menuitem = gtk_menu_item_new_with_label(_("Terminate All")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(TerminateAllTransTask), model); menuitem = gtk_menu_item_new_with_label(_("Clear Tasklist")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ClearTransTask), model); return menu; } /** * 为好友树(paltree)创建弹出菜单. * @param grpinf 好友群组信息 * @return 菜单 */ GtkWidget *MainWindow::CreatePaltreePopupMenu(GroupInfo *grpinf) { GtkWidget *menu, *menuitem; menu = gtk_menu_new(); /* 发送消息菜单 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Send Message")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: g_signal_connect_swapped( menuitem, "activate", G_CALLBACK(onPaltreePopupMenuSendMessageActivateRegular), grpinf); break; case GROUP_BELONG_TYPE_SEGMENT: case GROUP_BELONG_TYPE_GROUP: case GROUP_BELONG_TYPE_BROADCAST: g_signal_connect_swapped( menuitem, "activate", G_CALLBACK(onPaltreePopupMenuSendMessageActivateGroup), grpinf); break; default: gtk_widget_set_sensitive(menuitem, FALSE); break; } /* 请求共享文件菜单 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Request Shared Resources")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(AskSharedFiles), grpinf); break; default: gtk_widget_set_sensitive(menuitem, FALSE); break; } /* 改变好友信息数据菜单 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Change Info.")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(RevisePal::ReviseEntry), grpinf->member->data); break; default: gtk_widget_set_sensitive(menuitem, FALSE); break; } /* 删除好友项菜单 */ NO_OPERATION_C menuitem = gtk_menu_item_new_with_label(_("Delete Pal")); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(DeletePalItem), grpinf); break; default: gtk_widget_set_sensitive(menuitem, FALSE); break; } return menu; } /** * 填充好友数据到TextBuffer. * @param buffer text-buffer * @param pal class PalInfo */ void MainWindow::FillPalInfoToBuffer(GtkTextBuffer *buffer, PalInfo *pal) { char buf[MAX_BUFLEN], ipstr[INET_ADDRSTRLEN]; GtkTextIter iter; gtk_text_buffer_get_end_iter(buffer, &iter); snprintf(buf, MAX_BUFLEN, _("Version: %s\n"), pal->version); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (pal->group && *pal->group != '\0') snprintf(buf, MAX_BUFLEN, _("Nickname: %s@%s\n"), pal->name, pal->group); else snprintf(buf, MAX_BUFLEN, _("Nickname: %s\n"), pal->name); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("User: %s\n"), pal->user); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("Host: %s\n"), pal->host); gtk_text_buffer_insert(buffer, &iter, buf, -1); inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); if (pal->segdes && *pal->segdes != '\0') snprintf(buf, MAX_BUFLEN, _("Address: %s(%s)\n"), pal->segdes, ipstr); else snprintf(buf, MAX_BUFLEN, _("Address: %s\n"), ipstr); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (!FLAG_ISSET(pal->flags, 0)) snprintf(buf, MAX_BUFLEN, "%s", _("Compatibility: Microsoft\n")); else snprintf(buf, MAX_BUFLEN, "%s", _("Compatibility: GNU/Linux\n")); gtk_text_buffer_insert(buffer, &iter, buf, -1); snprintf(buf, MAX_BUFLEN, _("System coding: %s\n"), pal->encode); gtk_text_buffer_insert(buffer, &iter, buf, -1); if (pal->sign && *pal->sign != '\0') { gtk_text_buffer_insert(buffer, &iter, _("Signature:\n"), -1); gtk_text_buffer_insert_with_tags_by_name(buffer, &iter, pal->sign, -1, "sign-words", NULL); } } /** * 更新UI. * @param mwin 主窗口类 * @return Gtk+库所需 */ gboolean MainWindow::UpdateUI(MainWindow *mwin) { static uint32_t sumonline = 0; //避免每次都作一次设置 GtkWidget *widget; char buf[MAX_BUFLEN]; uint32_t sum; GSList *tlist; /* 统计当前在线人数 */ sum = 0; tlist = g_cthrd->GetPalList(); while (tlist) { if (FLAG_ISSET(((PalInfo *)tlist->data)->flags, 1)) sum++; tlist = g_slist_next(tlist); } /* 更新UI */ if (sumonline != sum) { snprintf(buf, MAX_BUFLEN, _("Pals Online: %" PRIu32), sum); widget = GTK_WIDGET(g_datalist_get_data(&mwin->widset, "online-label-widget")); gtk_label_set_text(GTK_LABEL(widget), buf); sumonline = sum; } return TRUE; } /** * 转到上一类结构树. * @param mwin 主窗口类 */ void MainWindow::GoPrevTreeModel(MainWindow *mwin) { GtkWidget *widget; GtkTreeModel *model; GtkTreeViewColumn *column; GList *tlist; widget = GTK_WIDGET(g_datalist_get_data(&mwin->widset, "paltree-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if ((tlist = g_list_find(mwin->tmdllist, model))) { if (tlist->prev) model = GTK_TREE_MODEL(tlist->prev->data); else model = GTK_TREE_MODEL(g_list_last(mwin->tmdllist)->data); gtk_tree_view_set_model(GTK_TREE_VIEW(widget), model); } column = GTK_TREE_VIEW_COLUMN(g_object_get_data(G_OBJECT(widget), "info-column")); gtk_tree_view_column_queue_resize(column); } /** * 转到下一类结构树. * @param mwin 主窗口类 */ void MainWindow::GoNextTreeModel(MainWindow *mwin) { GtkWidget *widget; GtkTreeModel *model; GtkTreeViewColumn *column; GList *tlist; widget = GTK_WIDGET(g_datalist_get_data(&mwin->widset, "paltree-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if ((tlist = g_list_find(mwin->tmdllist, model))) { if (tlist->next) model = GTK_TREE_MODEL(tlist->next->data); else model = GTK_TREE_MODEL(mwin->tmdllist->data); gtk_tree_view_set_model(GTK_TREE_VIEW(widget), model); } column = GTK_TREE_VIEW_COLUMN(g_object_get_data(G_OBJECT(widget), "info-column")); gtk_tree_view_column_queue_resize(column); } /** * 更新文件传输窗口UI. * @param treeview tree-view * @return GLib库所需 */ gboolean MainWindow::UpdateTransUI(GtkWidget *treeview) { GtkTreeModel *model; GtkTreeIter iter; TransAbstract *trans; GData **para; /* 考察是否需要更新UI */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); if (!gtk_tree_model_get_iter_first(model, &iter)) return TRUE; /* 更新UI */ do { gtk_tree_model_get(model, &iter, TRANS_TREE_MAX - 1, &trans, -1); if (trans) { //当文件传输类存在时才能更新 para = trans->GetTransFilePara(); //获取参数 /* 更新数据 */ gtk_list_store_set( GTK_LIST_STORE(model), &iter, 0, g_datalist_get_data(para, "status"), 1, g_datalist_get_data(para, "task"), 2, g_datalist_get_data(para, "peer"), 3, g_datalist_get_data(para, "ip"), 4, g_datalist_get_data(para, "filename"), 5, g_datalist_get_data(para, "filelength"), 6, g_datalist_get_data(para, "finishlength"), 7, GPOINTER_TO_INT(g_datalist_get_data(para, "progress")), 8, g_datalist_get_data(para, "pro-text"), 9, g_datalist_get_data(para, "cost"), 10, g_datalist_get_data(para, "remain"), 11, g_datalist_get_data(para, "rate"), 13, g_datalist_get_data(para, "data"), -1); } } while (gtk_tree_model_iter_next(model, &iter)); /* 重新调整UI */ gtk_tree_view_columns_autosize(GTK_TREE_VIEW(treeview)); return TRUE; } /** * 文件传输树(trans-tree)弹出操作菜单. * @param treeview tree-view * @param event event * @return Gtk+库所需 */ gboolean MainWindow::TransPopupMenu(GtkWidget *treeview, GdkEventButton *event) { GtkWidget *menu; GtkTreeModel *model; GtkTreePath *path; /* 检查事件是否可用 */ if (event->button != 3) return FALSE; /* 确定当前被选中的路径 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); if (gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview), GINT(event->x), GINT(event->y), &path, NULL, NULL, NULL)) g_object_set_data_full(G_OBJECT(model), "selected-path", path, GDestroyNotify(gtk_tree_path_free)); else g_object_set_data(G_OBJECT(model), "selected-path", NULL); /* 弹出菜单 */ menu = CreateTransPopupMenu(model); gtk_widget_show_all(menu); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event->button, event->time); return TRUE; } /** * 显示文件传输窗口. * @param widset widget set */ void MainWindow::ShowTransWindow(GData **widset) { GtkWidget *widget; guint timerid; widget = GTK_WIDGET(g_datalist_get_data(widset, "trans-window-widget")); gtk_widget_show(widget); gtk_window_present(GTK_WINDOW(widget)); widget = GTK_WIDGET(g_datalist_get_data(widset, "trans-treeview-widget")); timerid = gdk_threads_add_timeout(200, GSourceFunc(UpdateTransUI), widget); g_object_set_data(G_OBJECT(widget), "update-timer-id", GUINT_TO_POINTER(timerid)); } /** * 隐藏文件传输窗口. * @param widset widget set */ void MainWindow::HideTransWindow(GData **widset) { GtkWidget *widget; guint timerid; widget = GTK_WIDGET(g_datalist_get_data(widset, "trans-window-widget")); gtk_widget_hide(widget); widget = GTK_WIDGET(g_datalist_get_data(widset, "trans-treeview-widget")); timerid = GPOINTER_TO_UINT(g_object_get_data(G_OBJECT(widget), "update-timer-id")); g_source_remove(timerid); } /** * 清理文件传输任务. * @param widset widget set */ void MainWindow::ClearTransWindow(GData **widset) { GtkWidget *treeview; GtkTreeModel *model; /* 考察是否需要清理UI */ treeview = GTK_WIDGET(g_datalist_get_data(widset, "trans-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); ClearTransTask(model); /* 重新调整UI */ gtk_tree_view_columns_autosize(GTK_TREE_VIEW(treeview)); } /** * 终止单个传输任务. * @param model trans-model */ void MainWindow::TerminateTransTask(GtkTreeModel *model) { GtkTreePath *path; GtkTreeIter iter; TransAbstract *trans; if (!(path = (GtkTreePath *)(g_object_get_data(G_OBJECT(model), "selected-path")))) return; gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 12, &trans, -1); if (trans) trans->TerminateTrans(); } /** * 打开接收的文件. * @param model trans-model */ void MainWindow::OpenThisFile(GtkTreeModel *model) { GtkTreePath *path; GtkTreeIter iter; gchar *filename; if (!(path = (GtkTreePath *)(g_object_get_data(G_OBJECT(model), "selected-path")))) return; gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 12, &filename, -1); if (filename) { if (!g_file_test(filename, G_FILE_TEST_EXISTS)) { GtkWidget *dialog = gtk_message_dialog_new( NULL, GTK_DIALOG_MODAL, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, "%s", _("The file you want to open not exist!")); gtk_window_set_title(GTK_WINDOW(dialog), _("iptux Error")); gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); return; } iptux_open_url(filename); } } /** * 打开接收文件所在文件夹. * @param model trans-model */ void MainWindow::OpenContainingFolder(GtkTreeModel *model) { GtkTreePath *path; GtkTreeIter iter; gchar *filename, *filepath, *name; if (!(path = (GtkTreePath *)(g_object_get_data(G_OBJECT(model), "selected-path")))) return; gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 12, &filename, -1); if (filename) { name = ipmsg_get_filename_me(filename, &filepath); if (!g_file_test(filepath, G_FILE_TEST_EXISTS)) { GtkWidget *dialog = gtk_message_dialog_new( NULL, GTK_DIALOG_MODAL, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, "%s", _("The path you want to open not exist!")); gtk_window_set_title(GTK_WINDOW(dialog), "Iptux Error"); gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); return; } iptux_open_url(filepath); g_free(name); g_free(filepath); } } /** * 终止所有传输任务. * @param model trans-model */ void MainWindow::TerminateAllTransTask(GtkTreeModel *model) { GtkTreeIter iter; TransAbstract *trans; if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { gtk_tree_model_get(model, &iter, 12, &trans, -1); if (trans) trans->TerminateTrans(); } while (gtk_tree_model_iter_next(model, &iter)); } /** * 清理文件传输任务. * @param model trans-model */ void MainWindow::ClearTransTask(GtkTreeModel *model) { GtkTreeIter iter; gpointer data; if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { mark: gtk_tree_model_get(model, &iter, 12, &data, -1); if (!data) { if (gtk_list_store_remove(GTK_LIST_STORE(model), &iter)) goto mark; break; } } while (gtk_tree_model_iter_next(model, &iter)); } /** * 更新好友树. * @param mwin 主窗口类 */ void MainWindow::UpdatePalTree(MainWindow *mwin) { pthread_t pid; g_cthrd->Lock(); mwin->ClearAllItemFromPaltree(); g_cthrd->ClearAllPalFromList(); g_cthrd->Unlock(); pthread_create(&pid, NULL, ThreadFunc(CoreThread::SendNotifyToAll), g_cthrd); pthread_detach(pid); } /** * 请求此好友的共享文件. * @param grpinf 好友群组信息 */ void MainWindow::AskSharedFiles(GroupInfo *grpinf) { Command cmd; cmd.SendAskShared(g_cthrd->UdpSockQuote(), (PalInfo *)grpinf->member->data, 0, NULL); } /** * 删除好友项. * @param grpinf 好友群组信息 */ void MainWindow::DeletePalItem(GroupInfo *grpinf) { PalInfo *pal; /* 从UI中移除 */ if (g_mwin->PaltreeContainItem(grpinf->grpid)) g_mwin->DelItemFromPaltree(grpinf->grpid); g_cthrd->Lock(); /* 从数据中心点移除 */ if ((pal = g_cthrd->GetPalFromList(grpinf->grpid))) { g_cthrd->DelPalFromList(grpinf->grpid); FLAG_CLR(pal->flags, 1); } /* 加入黑名单 */ if (!g_cthrd->BlacklistContainItem(grpinf->grpid)) g_cthrd->AttachItemToBlacklist(grpinf->grpid); g_cthrd->Unlock(); } /** * 好友树(paltree)信息提示查询请求. * @param treeview the object which received the signal * @param x the x coordinate of the cursor position * @param y the y coordinate of the cursor position * @param key TRUE if the tooltip was trigged using the keyboard * @param tooltip a GtkTooltip * @return Gtk+库所需 */ gboolean MainWindow::PaltreeQueryTooltip(GtkWidget *treeview, gint x, gint y, gboolean key, GtkTooltip *tooltip, MainWindow *self) { GdkColor color = {0xff, 0xffff, 0xffff, 0xd6d8}; GtkWidget *textview; GtkTextBuffer *buffer; GtkTreePath *path; GtkTreeModel *model; GtkTreeIter iter; gint bx, by; GroupInfo *grpinf; gtk_tree_view_convert_widget_to_bin_window_coords(GTK_TREE_VIEW(treeview), x, y, &bx, &by); if (key || !gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview), bx, by, &path, NULL, NULL, NULL)) return FALSE; model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_path_free(path); gtk_tree_model_get(model, &iter, 6, &grpinf, -1); if (grpinf->type != GROUP_BELONG_TYPE_REGULAR) return FALSE; buffer = gtk_text_buffer_new(self->progdt.table); FillPalInfoToBuffer(buffer, (PalInfo *)grpinf->member->data); textview = gtk_text_view_new_with_buffer(buffer); gtk_text_view_set_cursor_visible(GTK_TEXT_VIEW(textview), FALSE); gtk_text_view_set_editable(GTK_TEXT_VIEW(textview), FALSE); gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(textview), GTK_WRAP_NONE); gtk_widget_modify_base(textview, GTK_STATE_NORMAL, &color); gtk_tooltip_set_custom(tooltip, textview); g_object_unref(buffer); return TRUE; } /** * 好友树(paltree)项被激活. * @param treeview the object on which the signal is emitted * @param path the GtkTreePath for the activated row * @param column the GtkTreeViewColumn in which the activation occurred */ void MainWindow::onPaltreeItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, MainWindow *self) { GtkTreeModel *model; GtkTreeIter iter; GroupInfo *grpinf; /* 获取项关联的群组数据 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 6, &grpinf, -1); /* 检查是否需要新建对话框 */ if (grpinf->dialog) { gtk_window_present(GTK_WINDOW(grpinf->dialog)); return; } /* 根据需求建立对应的对话框 */ switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: DialogPeer::PeerDialogEntry(self->config, grpinf, self->progdt); break; case GROUP_BELONG_TYPE_SEGMENT: case GROUP_BELONG_TYPE_GROUP: case GROUP_BELONG_TYPE_BROADCAST: DialogGroup::GroupDialogEntry(self->config, grpinf, self->progdt); default: break; } } /** * 好友树(paltree)弹出操作菜单. * @param treeview tree-view * @param event event * @return Gtk+库所需 */ gboolean MainWindow::PaltreePopupMenu(GtkWidget *treeview, GdkEventButton *event) { GtkWidget *menu; GtkTreeModel *model; GtkTreePath *path; GtkTreeIter iter; GroupInfo *grpinf; /* 检查事件是否可用 */ if (event->button != 3 || !gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview), GINT(event->x), GINT(event->y), &path, NULL, NULL, NULL)) return FALSE; /* 获取好友群组信息数据 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_path_free(path); gtk_tree_model_get(model, &iter, 6, &grpinf, -1); /* 弹出菜单 */ menu = CreatePaltreePopupMenu(grpinf); gtk_widget_show_all(menu); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, event->button, event->time); return TRUE; } /** * 展开或隐藏某行. * @param treeview text-view * @param event event * @return Gtk+库所需 */ gboolean MainWindow::PaltreeChangeStatus(GtkWidget *treeview, GdkEventButton *event) { GtkTreeModel *model; GtkCellRenderer *cell; GtkTreeViewColumn *column; GtkTreePath *path; GtkTreeIter iter; gint cellx, startpos, width; GroupInfo *grpinf; /* 检查事件的合法性 */ if (event->button != 1 || !gtk_tree_view_get_path_at_pos( GTK_TREE_VIEW(treeview), GINT(event->x), GINT(event->y), &path, &column, &cellx, NULL)) return FALSE; /* 检查此行是否可展开 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 6, &grpinf, -1); if (grpinf->type == GROUP_BELONG_TYPE_REGULAR) { gtk_tree_path_free(path); return FALSE; } /* 检查事件所发生的位置是否正确 */ cell = GTK_CELL_RENDERER(g_object_get_data(G_OBJECT(column), "expander-cell")); gtk_tree_view_column_cell_get_position(column, cell, &startpos, &width); if ((cellx < startpos) || (cellx > startpos + width)) { gtk_tree_path_free(path); return FALSE; } /* 展开或隐藏行 */ if (gtk_tree_view_row_expanded(GTK_TREE_VIEW(treeview), path)) gtk_tree_view_collapse_row(GTK_TREE_VIEW(treeview), path); else gtk_tree_view_expand_row(GTK_TREE_VIEW(treeview), path, FALSE); gtk_tree_path_free(path); return TRUE; } /** * 好友树(paltree)拖拽事件响应处理函数. * @param treeview tree-view * @param context the drag context * @param x where the drop happened * @param y where the drop happened * @param data the received data * @param info the info that has been registered with the target in the * GtkTargetList * @param time the timestamp at which the data was received */ void MainWindow::PaltreeDragDataReceived(GtkWidget *treeview, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time, MainWindow *self) { GtkTreeModel *model; GtkTreePath *path; GtkTreeIter iter; gint bx, by; GroupInfo *grpinf; SessionAbstract *session; GSList *list; /* 事件是否可用 */ gtk_tree_view_convert_widget_to_bin_window_coords(GTK_TREE_VIEW(treeview), x, y, &bx, &by); if (!gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview), bx, by, &path, NULL, NULL, NULL)) return; /* 获取好友群组信息数据 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_path_free(path); gtk_tree_model_get(model, &iter, 6, &grpinf, -1); /* 如果好友群组对话框尚未创建,则先创建对话框 */ if (!(grpinf->dialog)) { switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: DialogPeer::PeerDialogEntry(self->config, grpinf, self->progdt); break; case GROUP_BELONG_TYPE_SEGMENT: case GROUP_BELONG_TYPE_GROUP: case GROUP_BELONG_TYPE_BROADCAST: DialogGroup::GroupDialogEntry(self->config, grpinf, self->progdt); default: break; } } else gtk_window_present(GTK_WINDOW(grpinf->dialog)); /* 获取会话对象,并将数据添加到会话对象 */ session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); list = selection_data_get_path(data); //获取所有文件 session->AttachEnclosure(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); // session->ShowEnclosure(); } /** * 好友树(paltree)按昵称排序的比较函数. * @param model paltree-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint MainWindow::PaltreeCompareByNameFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { GroupInfo *agrpinf, *bgrpinf; gint result; gtk_tree_model_get(model, a, 6, &agrpinf, -1); gtk_tree_model_get(model, b, 6, &bgrpinf, -1); result = strcmp(agrpinf->name, bgrpinf->name); return result; } /** * 好友树(paltree)按IP排序的比较函数. * @param model paltree-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint MainWindow::PaltreeCompareByIPFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { GroupInfo *agrpinf, *bgrpinf; gint result; gtk_tree_model_get(model, a, 6, &agrpinf, -1); gtk_tree_model_get(model, b, 6, &bgrpinf, -1); if (agrpinf->type == GROUP_BELONG_TYPE_REGULAR && bgrpinf->type == GROUP_BELONG_TYPE_REGULAR) result = ntohl(agrpinf->grpid) - ntohl(bgrpinf->grpid); else result = 0; return result; } /** * 设置好友树(paltree)的比较函数. * @param menuitem radio-menu-item * @param mdlset model set */ void MainWindow::SetPaltreeSortFunc(GtkWidget *menuitem, GData **mdlset) { GtkTreeIterCompareFunc func; GtkTreeModel *model; if (!gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(menuitem))) return; func = (GtkTreeIterCompareFunc)( g_object_get_data(G_OBJECT(menuitem), "compare-func")); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "regular-paltree-model")); gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(model), func, NULL, NULL); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "segment-paltree-model")); gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(model), func, NULL, NULL); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "group-paltree-model")); gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(model), func, NULL, NULL); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "broadcast-paltree-model")); gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(model), func, NULL, NULL); } /** * 设置好友树(paltree)的排序方式. * @param menuitem radio-menu-item * @param mdlset model set */ void MainWindow::SetPaltreeSortType(GtkWidget *menuitem, GData **mdlset) { GtkSortType type; GtkTreeModel *model; if (!gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(menuitem))) return; type = (GtkSortType)GPOINTER_TO_INT( g_object_get_data(G_OBJECT(menuitem), "sort-type")); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "regular-paltree-model")); gtk_tree_sortable_set_sort_column_id( GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, type); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "segment-paltree-model")); gtk_tree_sortable_set_sort_column_id( GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, type); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "group-paltree-model")); gtk_tree_sortable_set_sort_column_id( GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, type); model = GTK_TREE_MODEL(g_datalist_get_data(mdlset, "broadcast-paltree-model")); gtk_tree_sortable_set_sort_column_id( GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, type); } /** * 显示好友清单区域. * @param widset widget set */ void MainWindow::ShowPallistArea(GData **widset) { GtkWidget *widget; widget = GTK_WIDGET(g_datalist_get_data(widset, "pallist-box-widget")); gtk_widget_show(widget); widget = GTK_WIDGET(g_datalist_get_data(widset, "pallist-entry-widget")); gtk_widget_grab_focus(widget); PallistEntryChanged(widget, widset); } /** * 隐藏好友清单区域. * @param widset widget set */ void MainWindow::HidePallistArea(GData **widset) { GtkWidget *widget; GtkTreeModel *model; widget = GTK_WIDGET(g_datalist_get_data(widset, "pallist-box-widget")); gtk_widget_hide(widget); widget = GTK_WIDGET(g_datalist_get_data(widset, "pallist-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); gtk_list_store_clear(GTK_LIST_STORE(model)); widget = GTK_WIDGET(g_datalist_get_data(widset, "pallist-entry-widget")); gtk_editable_delete_text(GTK_EDITABLE(widget), 0, -1); } /** * 清空好友清单搜索输入框. * @param entry entry * @param event event * @return Gtk+库所需 */ gboolean MainWindow::ClearPallistEntry(GtkWidget *entry, GdkEventKey *event) { if (event->keyval != GDK_KEY_Escape) return FALSE; gtk_editable_delete_text(GTK_EDITABLE(entry), 0, -1); return TRUE; } /** * 好友清单搜索输入框内容变更响应处理函数. * @param entry entry * @param widset widget set */ void MainWindow::PallistEntryChanged(GtkWidget *entry, GData **widset) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkWidget *treeview; GtkTreeModel *model; GtkTreeIter iter; char ipstr[INET_ADDRSTRLEN], *file; const gchar *text; GSList *tlist; PalInfo *pal; /* 获取默认主题 */ theme = gtk_icon_theme_get_default(); /* 获取搜索内容 */ text = gtk_entry_get_text(GTK_ENTRY(entry)); /* 获取好友清单,并清空 */ treeview = GTK_WIDGET(g_datalist_get_data(widset, "pallist-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_list_store_clear(GTK_LIST_STORE(model)); /* 将符合条件的好友加入好友清单 */ tlist = g_cthrd->GetPalList(); while (tlist) { pal = (PalInfo *)tlist->data; inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); /* Search friends case ingore is better. */ if (*text == '\0' || strcasestr(pal->name, text) || (pal->group && strcasestr(pal->group, text)) || strcasestr(ipstr, text) || strcasestr(pal->user, text) || strcasestr(pal->host, text)) { file = iptux_erase_filename_suffix(pal->iconfile); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, pal->name, 2, pal->group, 3, ipstr, 4, pal->user, 5, pal->host, 6, pal, -1); if (pixbuf) g_object_unref(pixbuf); } tlist = g_slist_next(tlist); } /* 重新调整好友清单UI */ gtk_tree_view_columns_autosize(GTK_TREE_VIEW(treeview)); } /** * 好友清单(pallist)项被激活. * @param treeview the object on which the signal is emitted * @param path the GtkTreePath for the activated row * @param column the GtkTreeViewColumn in which the activation occurred */ void MainWindow::PallistItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, MainWindow *self) { GtkTreeModel *model; GtkTreeIter iter; GroupInfo *grpinf; PalInfo *pal; model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, 6, &pal, -1); if ((grpinf = g_cthrd->GetPalRegularItem(pal))) { if (!(grpinf->dialog)) DialogPeer::PeerDialogEntry(self->config, grpinf, self->progdt); else gtk_window_present(GTK_WINDOW(grpinf->dialog)); } } /** * 好友清单(pallist)拖拽事件响应处理函数. * @param treeview tree-view * @param context the drag context * @param x where the drop happened * @param y where the drop happened * @param data the received data * @param info the info that has been registered with the target in the * GtkTargetList * @param time the timestamp at which the data was received */ void MainWindow::PallistDragDataReceived(GtkWidget *treeview, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time, MainWindow *self) { GtkTreeModel *model; GtkTreePath *path; GtkTreeIter iter; gint bx, by; GroupInfo *grpinf; PalInfo *pal; SessionAbstract *session; GSList *list; /* 事件是否可用 */ gtk_tree_view_convert_widget_to_bin_window_coords(GTK_TREE_VIEW(treeview), x, y, &bx, &by); if (!gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(treeview), bx, by, &path, NULL, NULL, NULL)) return; /* 获取好友群组信息数据 */ model = gtk_tree_view_get_model(GTK_TREE_VIEW(treeview)); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_path_free(path); gtk_tree_model_get(model, &iter, 6, &pal, -1); if (!(grpinf = g_cthrd->GetPalRegularItem(pal))) return; /* 如果好友群组对话框尚未创建,则先创建对话框 */ if (!(grpinf->dialog)) DialogPeer::PeerDialogEntry(self->config, grpinf, self->progdt); else gtk_window_present(GTK_WINDOW(grpinf->dialog)); /* 获取会话对象,并将数据添加到会话对象 */ session = (SessionAbstract *)g_object_get_data(G_OBJECT(grpinf->dialog), "session-class"); list = selection_data_get_path(data); //获取所有文件 session->AttachEnclosure(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); // session->ShowEnclosure(); } /** * 主窗口位置&大小改变的响应处理函数. * @param window 主窗口 * @param event the GdkEventConfigure which triggered this signal * @param dtset data set * @return Gtk+库所需 */ gboolean MainWindow::MWinConfigureEvent(GtkWidget *window, GdkEventConfigure *event, MainWindow *self) { self->windowConfig.SetWidth(event->width) .SetHeight(event->height) .SaveToConfig(self->config); return FALSE; } /** * 文件传输窗口位置&大小改变的响应处理函数. * @param window 文件传输窗口 * @param event the GdkEventConfigure which triggered this signal * @param dtset data set * @return Gtk+库所需 */ gboolean MainWindow::TWinConfigureEvent(GtkWidget *window, GdkEventConfigure *event, MainWindow *self) { self->config.SetInt("trans_window_width", event->width); self->config.SetInt("trans_window_height", event->height); self->config.Save(); return FALSE; } /** * 分割面板的分割位置改变的响应处理函数. * @param paned paned * @param pspec he GParamSpec of the property which changed * @param dtset data set */ void MainWindow::PanedDivideChanged(GtkWidget *paned, GParamSpec *pspec, MainWindow *self) { self->config.SetInt("mwin_main_paned_divide", gtk_paned_get_position(GTK_PANED(paned))); self->config.Save(); } gboolean MainWindow::onDeleteEvent(MainWindow *self) { return self->statusIcon->AlterInterfaceMode(); } void MainWindow::onPaltreePopupMenuSendMessageActivateRegular( GroupInfo *groupInfo) { DialogPeer::PeerDialogEntry(g_mwin->getConfig(), groupInfo, *g_progdt); } void MainWindow::onPaltreePopupMenuSendMessageActivateGroup( GroupInfo *groupInfo) { DialogGroup::GroupDialogEntry(g_mwin->getConfig(), groupInfo, *g_progdt); } } // namespace iptux iptux-0.7.4/src/iptux/MainWindow.h000066400000000000000000000154511323207530100170620ustar00rootroot00000000000000// // C++ Interface: MainWindow // // Description: // 创建程序主窗口 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_MAINWINDOW_H #define IPTUX_MAINWINDOW_H #include "iptux/IptuxConfig.h" #include "iptux/ProgramData.h" #include "iptux/WindowConfig.h" #include "iptux/mess.h" namespace iptux { class StatusIcon; /** * @note 鉴于本类成员函数所访问的(CoreThread)类成员链表都具有只增不减的特性, * 所以无须加锁访问,若有例外,请于注释中说明,否则应当bug处理.\n * 若此特性不可被如此利用,请报告bug. */ class MainWindow { public: MainWindow(IptuxConfig &config, ProgramData &progdt); ~MainWindow(); void CreateWindow(); void AlterWindowMode(); GtkWidget *ObtainWindow(); bool PaltreeContainItem(in_addr_t ipv4); void UpdateItemToPaltree(in_addr_t ipv4); void AttachItemToPaltree(in_addr_t ipv4); void DelItemFromPaltree(in_addr_t ipv4); void ClearAllItemFromPaltree(); void MakeItemBlinking(GroupInfo *grpinf, bool blinking); void OpenTransWindow(); void UpdateItemToTransTree(GData **para); bool TransmissionActive(); ProgramData &GetProgramData() { return progdt; } IptuxConfig &getConfig() { return config; } void SetStatusIcon(StatusIcon *statusIcon) { this->statusIcon = statusIcon; } private: IptuxConfig &config; ProgramData &progdt; StatusIcon *statusIcon; GData *widset; //窗体集 GData *mdlset; //数据model集 // GData *dtset; //通用数据集 GList *tmdllist; // model链表,用于构建model循环结构 GtkAccelGroup *accel; //快捷键集组 guint timerid; // UI更新定时器ID WindowConfig windowConfig; private: void InitSublayer(); void ClearSublayer(); GtkWidget *CreateMainWindow(); GtkWidget *CreateTransWindow(); GtkWidget *CreateAllArea(); GtkWidget *CreateTransArea(); GtkWidget *CreateMenuBar(); GtkWidget *CreateToolBar(); GtkWidget *CreatePaltreeArea(); GtkWidget *CreatePallistArea(); GtkWidget *CreateFileMenu(); GtkWidget *CreateToolMenu(); GtkWidget *CreateHelpMenu(); GtkTreeModel *CreatePaltreeModel(); GtkTreeModel *CreatePallistModel(); GtkTreeModel *CreateTransModel(); GtkWidget *CreatePaltreeTree(GtkTreeModel *model); GtkWidget *CreatePallistTree(GtkTreeModel *model); GtkWidget *CreateTransTree(GtkTreeModel *model); bool GroupGetPrevPaltreeItem(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf); bool GroupGetPaltreeItem(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf); bool GroupGetPaltreeItemWithParent(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf); void FillGroupInfoToPaltree(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf); void UpdateGroupInfoToPaltree(GtkTreeModel *model, GtkTreeIter *iter, GroupInfo *grpinf); void BlinkGroupItemToPaltree(GtkTreeModel *model, GtkTreeIter *iter, bool blinking); static GtkWidget *CreateTransPopupMenu(GtkTreeModel *model); static GtkWidget *CreatePaltreePopupMenu(GroupInfo *grpinf); static void FillPalInfoToBuffer(GtkTextBuffer *buffer, PalInfo *pal); //回调处理部分 private: static gboolean UpdateUI(MainWindow *mwin); static void GoPrevTreeModel(MainWindow *mwin); static void GoNextTreeModel(MainWindow *mwin); static gboolean UpdateTransUI(GtkWidget *treeview); static gboolean TransPopupMenu(GtkWidget *treeview, GdkEventButton *event); static void ShowTransWindow(GData **widset); static void HideTransWindow(GData **widset); static void ClearTransWindow(GData **widset); static void TerminateTransTask(GtkTreeModel *model); static void TerminateAllTransTask(GtkTreeModel *model); static void ClearTransTask(GtkTreeModel *model); static void OpenContainingFolder(GtkTreeModel *model); static void OpenThisFile(GtkTreeModel *model); static void UpdatePalTree(MainWindow *mwin); static void AskSharedFiles(GroupInfo *grpinf); static void DeletePalItem(GroupInfo *grpinf); static gboolean PaltreeQueryTooltip(GtkWidget *treeview, gint x, gint y, gboolean key, GtkTooltip *tooltip, MainWindow *self); static void onPaltreeItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, MainWindow *self); static gboolean PaltreePopupMenu(GtkWidget *treeview, GdkEventButton *event); static void onPaltreePopupMenuSendMessageActivateRegular( GroupInfo *groupInfo); static void onPaltreePopupMenuSendMessageActivateGroup(GroupInfo *groupInfo); static gboolean PaltreeChangeStatus(GtkWidget *treeview, GdkEventButton *event); static void PaltreeDragDataReceived(GtkWidget *treeview, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time, MainWindow *self); static gint PaltreeCompareByNameFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); static gint PaltreeCompareByIPFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); static void SetPaltreeSortFunc(GtkWidget *menuitem, GData **mdlset); static void SetPaltreeSortType(GtkWidget *menuitem, GData **mdlset); static void ShowPallistArea(GData **widset); static void HidePallistArea(GData **widset); static gboolean ClearPallistEntry(GtkWidget *entry, GdkEventKey *event); static void PallistEntryChanged(GtkWidget *entry, GData **widset); static void PallistItemActivated(GtkWidget *treeview, GtkTreePath *path, GtkTreeViewColumn *column, MainWindow *self); static void PallistDragDataReceived(GtkWidget *treeview, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time, MainWindow *self); static gboolean MWinConfigureEvent(GtkWidget *window, GdkEventConfigure *event, MainWindow *self); static gboolean TWinConfigureEvent(GtkWidget *window, GdkEventConfigure *event, MainWindow *self); static void PanedDivideChanged(GtkWidget *paned, GParamSpec *pspec, MainWindow *self); static gboolean onDeleteEvent(MainWindow *self); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/ProgramData.cpp000066400000000000000000000230141323207530100175340ustar00rootroot00000000000000// // C++ Implementation: ProgramData // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "ProgramData.h" #include #include "iptux/CoreThread.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/ipmsg.h" #include "iptux/utils.h" using namespace std; namespace iptux { /** * 类构造函数. */ ProgramData::ProgramData(IptuxConfig &config) : palicon(NULL), font(NULL), transtip(NULL), msgtip(NULL), volume(1.0), sndfgs(~0), netseg(NULL), urlregex(NULL), xcursor(NULL), lcursor(NULL), table(NULL), config(config), flags(0) { gettimeofday(×tamp, NULL); pthread_mutex_init(&mutex, NULL); } /** * 类析构函数. */ ProgramData::~ProgramData() { g_free(palicon); g_free(font); g_free(msgtip); g_free(transtip); for (GSList *tlist = netseg; tlist; tlist = g_slist_next(tlist)) delete (NetSegment *)tlist->data; g_slist_free(netseg); if (urlregex) g_regex_unref(urlregex); if (xcursor) gdk_cursor_unref(xcursor); if (lcursor) gdk_cursor_unref(lcursor); if (table) g_object_unref(table); pthread_mutex_destroy(&mutex); } /** * 初始化相关类成员数据. */ void ProgramData::InitSublayer() { ReadProgData(); CheckIconTheme(); CreateRegex(); CreateCursor(); CreateTagTable(); } /** * 写出程序数据. */ void ProgramData::WriteProgData() { gettimeofday(×tamp, NULL); //更新时间戳 config.SetString("nick_name", nickname); config.SetString("belong_group", mygroup); config.SetString("my_icon", myicon); config.SetString("archive_path", path); config.SetString("personal_sign", sign); config.SetString("candidacy_encode", codeset); config.SetString("preference_encode", encode); config.SetString("pal_icon", palicon); config.SetString("panel_font", font); config.SetBool("open_chat", FLAG_ISSET(flags, 7)); config.SetBool("hide_startup", FLAG_ISSET(flags, 6)); config.SetBool("open_transmission", FLAG_ISSET(flags, 5)); config.SetBool("use_enter_key", FLAG_ISSET(flags, 4)); config.SetBool("clearup_history", FLAG_ISSET(flags, 3)); config.SetBool("record_log", FLAG_ISSET(flags, 2)); config.SetBool("open_blacklist", FLAG_ISSET(flags, 1)); config.SetBool("proof_shared", FLAG_ISSET(flags, 0)); config.SetString("trans_tip", transtip); config.SetString("msg_tip", msgtip); config.SetDouble("volume_degree", volume); config.SetBool("transnd_support", FLAG_ISSET(sndfgs, 2)); config.SetBool("msgsnd_support", FLAG_ISSET(sndfgs, 1)); config.SetBool("sound_support", FLAG_ISSET(sndfgs, 0)); config.Save(); WriteNetSegment(); } /** * 深拷贝一份网段数据. * @return 网段数据 */ GSList *ProgramData::CopyNetSegment() { NetSegment *ns, *pns; GSList *tlist, *nseg; nseg = NULL; tlist = netseg; while (tlist) { pns = (NetSegment *)tlist->data; ns = new NetSegment; nseg = g_slist_append(nseg, ns); ns->startip = g_strdup(pns->startip); ns->endip = g_strdup(pns->endip); ns->description = g_strdup(pns->description); tlist = g_slist_next(tlist); } return nseg; } /** * 查询(ipv4)所在网段的描述串. * @param ipv4 ipv4 * @return 描述串 */ char *ProgramData::FindNetSegDescription(in_addr_t ipv4) { in_addr_t startip, endip; NetSegment *pns; GSList *tlist; char *description; ipv4 = ntohl(ipv4); description = NULL; tlist = netseg; while (tlist) { pns = (NetSegment *)tlist->data; inet_pton(AF_INET, pns->startip, &startip); startip = ntohl(startip); inet_pton(AF_INET, pns->endip, &endip); endip = ntohl(endip); ipv4_order(&startip, &endip); if (ipv4 >= startip && ipv4 <= endip) { description = g_strdup(pns->description); break; } tlist = g_slist_next(tlist); } return description; } /** * 读取程序数据. */ void ProgramData::ReadProgData() { nickname = config.GetString("nick_name", g_get_user_name()); mygroup = config.GetString("belong_group"); myicon = config.GetString("my_icon", "icon-tux.png"); path = config.GetString("archive_path", g_get_home_dir()); sign = config.GetString("personal_sign"); codeset = config.GetString("candidacy_encode", "utf-16"); encode = config.GetString("preference_encode", "utf-8"); palicon = g_strdup(config.GetString("pal_icon", "icon-qq.png").c_str()); font = g_strdup(config.GetString("panel_font", "Sans Serif 10").c_str()); FLAG_SET(flags, 7, config.GetBool("open_chat")); FLAG_SET(flags, 6, config.GetBool("hide_startup")); FLAG_SET(flags, 5, config.GetBool("open_transmission")); FLAG_SET(flags, 4, config.GetBool("use_enter_key")); FLAG_SET(flags, 3, config.GetBool("clearup_history")); FLAG_SET(flags, 2, config.GetBool("record_log")); FLAG_SET(flags, 1, config.GetBool("open_blacklist")); FLAG_SET(flags, 0, config.GetBool("proof_shared")); msgtip = g_strdup(config.GetString("msg_tip", __SOUND_PATH "/msg.ogg").c_str()); transtip = g_strdup( config.GetString("trans_tip", __SOUND_PATH "/trans.ogg").c_str()); volume = config.GetDouble("volume_degree"); FLAG_SET(flags, 2, config.GetBool("transnd_support")); FLAG_SET(flags, 1, config.GetBool("msgsnd_support")); FLAG_SET(flags, 0, config.GetBool("sound_support")); } /** * 确保头像数据被存放在主题库中. */ void ProgramData::CheckIconTheme() { char pathbuf[MAX_PATHLEN]; GdkPixbuf *pixbuf; snprintf(pathbuf, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", myicon.c_str()); if (access(pathbuf, F_OK) != 0) { snprintf(pathbuf, MAX_PATHLEN, "%s" ICON_PATH "/%s", g_get_user_config_dir(), myicon.c_str()); if ((pixbuf = gdk_pixbuf_new_from_file(pathbuf, NULL))) { gtk_icon_theme_add_builtin_icon(myicon.c_str(), MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } } snprintf(pathbuf, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", palicon); if (access(pathbuf, F_OK) != 0) { snprintf(pathbuf, MAX_PATHLEN, "%s" ICON_PATH "/%s", g_get_user_config_dir(), palicon); if ((pixbuf = gdk_pixbuf_new_from_file(pathbuf, NULL))) { gtk_icon_theme_add_builtin_icon(palicon, MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } } } /** * 创建识别URL的正则表达式. */ void ProgramData::CreateRegex() { urlregex = g_regex_new(URL_REGEX, GRegexCompileFlags(0), GRegexMatchFlags(0), NULL); } /** * 创建鼠标光标. */ void ProgramData::CreateCursor() { xcursor = gdk_cursor_new(GDK_XTERM); lcursor = gdk_cursor_new(GDK_HAND2); } /** * 创建用于(text-view)的一些通用tag. * @note 给这些tag一个"global"标记,表示这些对象是全局共享的 */ void ProgramData::CreateTagTable() { GtkTextTag *tag; table = gtk_text_tag_table_new(); tag = gtk_text_tag_new("pal-color"); g_object_set(tag, "foreground", "blue", NULL); g_object_set_data(G_OBJECT(tag), "global", GINT_TO_POINTER(TRUE)); gtk_text_tag_table_add(table, tag); g_object_unref(tag); tag = gtk_text_tag_new("me-color"); g_object_set(tag, "foreground", "green", NULL); g_object_set_data(G_OBJECT(tag), "global", GINT_TO_POINTER(TRUE)); gtk_text_tag_table_add(table, tag); g_object_unref(tag); tag = gtk_text_tag_new("error-color"); g_object_set(tag, "foreground", "red", NULL); g_object_set_data(G_OBJECT(tag), "global", GINT_TO_POINTER(TRUE)); gtk_text_tag_table_add(table, tag); g_object_unref(tag); tag = gtk_text_tag_new("sign-words"); g_object_set(tag, "indent", 10, "foreground", "#1005F0", "font", "Sans Italic 8", NULL); g_object_set_data(G_OBJECT(tag), "global", GINT_TO_POINTER(TRUE)); gtk_text_tag_table_add(table, tag); g_object_unref(tag); tag = gtk_text_tag_new("url-link"); g_object_set(tag, "foreground", "blue", "underline", PANGO_UNDERLINE_SINGLE, NULL); g_object_set_data(G_OBJECT(tag), "global", GINT_TO_POINTER(TRUE)); gtk_text_tag_table_add(table, tag); g_object_unref(tag); } /** * 写出网段数据. */ void ProgramData::WriteNetSegment() { vector jsons; pthread_mutex_lock(&mutex); GSList *tlist = netseg; while (tlist) { NetSegment *pns = (NetSegment *)tlist->data; jsons.push_back(pns->ToJsonValue()); tlist = g_slist_next(tlist); } pthread_mutex_unlock(&mutex); config.SetVector("scan_net_segement", jsons); } /** * 读取网段数据. * @param client GConfClient */ void ProgramData::ReadNetSegment() { vector values = config.GetVector("scan_net_segment"); for (size_t i = 0; i < values.size(); ++i) { NetSegment *segment = NetSegment::NewFromJsonValue(values[i]); netseg = g_slist_append(netseg, segment); } } void ProgramData::Lock() { pthread_mutex_lock(&mutex); } void ProgramData::Unlock() { pthread_mutex_unlock(&mutex); } bool ProgramData::IsAutoOpenCharDialog() const { return FLAG_ISSET(flags, 7); } bool ProgramData::IsAutoHidePanelAfterLogin() const { return FLAG_ISSET(flags, 6); } bool ProgramData::IsAutoOpenFileTrans() const { return FLAG_ISSET(flags, 5); } bool ProgramData::IsEnterSendMessage() const { return FLAG_ISSET(flags, 4); } bool ProgramData::IsAutoCleanChatHistory() const { return FLAG_ISSET(flags, 3); } bool ProgramData::IsSaveChatHistory() const { return FLAG_ISSET(flags, 2); } bool ProgramData::IsUsingBlacklist() const { return FLAG_ISSET(flags, 1); } bool ProgramData::IsFilterFileShareRequest() const { return FLAG_ISSET(flags, 0); } void ProgramData::SetFlag(int idx, bool flag) { if (flag) { FLAG_SET(flags, idx); } else { FLAG_CLR(flags, idx); } } } // namespace iptuxiptux-0.7.4/src/iptux/ProgramData.h000066400000000000000000000053061323207530100172050ustar00rootroot00000000000000// // C++ Interface: ProgramData // // Description: 与iptux相关的程序数据 // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_PROGRAMDATA_H #define IPTUX_PROGRAMDATA_H #include #include #include "iptux/IptuxConfig.h" namespace iptux { /* flags // 消息(:7);当有消息时自动打开聊天窗口 // 图标(:6);程序启动后只显示托盘图标而不显示面板 // 传输(:5);当有文件传输时自动打开文件传输窗口 // enter(:4);使用Enter键发送消息 // 历史(:3);关闭好友对话框后自动清空聊天历史 // 日志(:2);开启日志记录功能 // 黑名单(:1);不允许删除的好友再出现 // 共享(:0);好友请求本人的共享文件时需要得到确认 *//* sndfgs // 传输(:2);文件传输完成后需要播放提示音 // 消息(:1);有消息到来后需要播放提示音 // 声音(:0);是否需要提示音 */ class ProgramData { public: explicit ProgramData(IptuxConfig &config); ~ProgramData(); void InitSublayer(); void WriteProgData(); GSList *CopyNetSegment(); char *FindNetSegDescription(in_addr_t ipv4); void Lock(); void Unlock(); bool IsAutoOpenCharDialog() const; bool IsAutoHidePanelAfterLogin() const; bool IsAutoOpenFileTrans() const; bool IsEnterSendMessage() const; bool IsAutoCleanChatHistory() const; bool IsSaveChatHistory() const; bool IsUsingBlacklist() const; bool IsFilterFileShareRequest() const; void SetFlag(int idx, bool flag); std::string nickname; //昵称 * std::string mygroup; //所属群组 * std::string myicon; //个人头像 * std::string path; //存档路径 * std::string sign; //个性签名 * std::string codeset; //候选编码 * std::string encode; //默认通信编码 * char *palicon; //默认头像 * char *font; //面板字体 * char *transtip; //传输完成提示声音 * char *msgtip; //消息到来提示声音 * double volume; //音量控制 uint8_t sndfgs; // 2 传输:1 消息:0 声音 GSList *netseg; //需要通知登录的IP段 GRegex *urlregex; // URL正则表达式 GdkCursor *xcursor, *lcursor; //光标 GtkTextTagTable *table; // tag table struct timeval timestamp; //程序数据时间戳 private: IptuxConfig &config; pthread_mutex_t mutex; //锁 uint8_t flags; // 6 图标,5 传输:4 enter:3 历史:2 日志:1 黑名单:0 共享 private: void ReadProgData(); void AddGconfNotify(); void CheckIconTheme(); void CreateRegex(); void CreateCursor(); void CreateTagTable(); void WriteNetSegment(); void ReadNetSegment(); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/RecvFile.cpp000066400000000000000000000044351323207530100170400ustar00rootroot00000000000000// // C++ Implementation: RecvFile // // Description: // // // Author: cwll ,(C) 2012.02 // Jally , (C) 2008 // 2012.02:把文件接收确认和选择放在了聊天窗口,所以这个类的大部分功能都不用了 // // Copyright: See COPYING file that comes with this distribution // // #include "RecvFile.h" #include #include "iptux/ProgramData.h" #include "iptux/RecvFileData.h" #include "iptux/callback.h" #include "iptux/global.h" #include "iptux/utils.h" using namespace std; namespace iptux { /** * 类构造函数. */ RecvFile::RecvFile() {} /** * 类析构函数. */ RecvFile::~RecvFile() {} /** * 文件接受入口. * @param para 文件参数 */ void RecvFile::RecvEntry(GData *para) { RecvFile *rfile; rfile = new RecvFile; rfile->ParseFilePara(¶); g_datalist_clear(¶); // para提供的数据已经没用了,秒掉它 delete rfile; //待接上文件的信息已存入中心节点可以删除了 } /** * 分析文件参数. * @param para 文件参数 */ void RecvFile::ParseFilePara(GData **para) { PalInfo *pal; FileInfo *file; char *extra; uint32_t packetn; pal = (PalInfo *)g_datalist_get_data(para, "palinfo"); extra = (char *)g_datalist_get_data(para, "extra-data"); packetn = GPOINTER_TO_UINT(g_datalist_get_data(para, "packetno")); while (extra && *extra) { file = DivideFileinfo(&extra); file->packetn = packetn; file->fileown = pal; g_cthrd->PushItemToEnclosureList(file); } } /** * 从文件信息串中分离出文件信息数据. * @param extra 文件信息串 * @return 文件信息数据 */ FileInfo *RecvFile::DivideFileinfo(char **extra) { FileInfo *file; file = new FileInfo; file->fileid = iptux_get_dec_number(*extra, ':', 0); file->fileattr = iptux_get_hex_number(*extra, ':', 4); file->filesize = iptux_get_hex64_number(*extra, ':', 2); file->filepath = ipmsg_get_filename(*extra, ':', 1); file->filectime = iptux_get_hex_number(*extra, ':', 3); file->finishedsize = 0; //分割,格式1(\a) 格式2(:\a) 格式3(\a:) 格式4(:\a:) *extra = strchr(*extra, '\a'); if (*extra) //跳过'\a'字符 (*extra)++; if (*extra && (**extra == ':')) //跳过可能存在的':'字符 (*extra)++; return file; } } // namespace iptux iptux-0.7.4/src/iptux/RecvFile.h000066400000000000000000000012641323207530100165020ustar00rootroot00000000000000// // C++ Interface: RecvFile // // Description: // 接受相关的文件信息,不包含文件数据 // // Author: cwll ,(C) 2012.02 // Jally , (C) 2008 // 2012.02:把文件接收确认和选择放在了聊天窗口,所以这个类的大部分功能都不用了 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_RECVFILE_H #define IPTUX_RECVFILE_H #include "iptux/mess.h" namespace iptux { class RecvFile { public: RecvFile(); ~RecvFile(); static void RecvEntry(GData *para); private: void ParseFilePara(GData **para); FileInfo *DivideFileinfo(char **extra); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/RecvFileData.cpp000066400000000000000000000336401323207530100176320ustar00rootroot00000000000000// // C++ Implementation: RecvFileData // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "RecvFileData.h" #include #include #include #include "iptux/AnalogFS.h" #include "iptux/Command.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/ipmsg.h" #include "iptux/output.h" #include "iptux/utils.h" #include "iptux/wrapper.h" namespace iptux { /** * 类构造函数. * @param fl 文件信息数据 */ RecvFileData::RecvFileData(FileInfo *fl) : file(fl), para(NULL), terminate(false), sumsize(0) { g_datalist_init(¶); gettimeofday(&tasktime, NULL); /* gettimeofday(&filetime, NULL);//个人感觉没必要 */ } /** * 类析构函数. */ RecvFileData::~RecvFileData() { g_datalist_clear(¶); } /** * 接收文件数据入口. */ void RecvFileData::RecvFileDataEntry() { /* 创建UI参考数据,并将数据主动加入UI */ gdk_threads_enter(); CreateUIPara(); g_mwin->UpdateItemToTransTree(¶); if (g_progdt->IsAutoOpenFileTrans()) { g_mwin->OpenTransWindow(); } gdk_threads_leave(); /* 分类处理 */ switch (GET_MODE(file->fileattr)) { case IPMSG_FILE_REGULAR: RecvRegularFile(); break; case IPMSG_FILE_DIR: RecvDirFiles(); break; default: break; } /* 主动更新UI */ gdk_threads_enter(); UpdateUIParaToOver(); g_mwin->UpdateItemToTransTree(¶); gdk_threads_leave(); /* 处理成功则播放提示音 */ if (!terminate && FLAG_ISSET(g_progdt->sndfgs, 2)) g_sndsys->Playing(g_progdt->transtip); } /** * 获取UI参考数据. * @return UI参考数据 */ GData **RecvFileData::GetTransFilePara() { return ¶ } /** * 终止过程处理. */ void RecvFileData::TerminateTrans() { terminate = true; } /** * 创建UI参考数据. */ void RecvFileData::CreateUIPara() { GtkIconTheme *theme; GdkPixbuf *pixbuf; struct in_addr addr; theme = gtk_icon_theme_get_default(); if ((pixbuf = gtk_icon_theme_load_icon(theme, "tip-recv", MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) g_datalist_set_data_full(¶, "status", pixbuf, GDestroyNotify(g_object_unref)); g_datalist_set_data(¶, "task", (gpointer)(_("receive"))); g_datalist_set_data_full(¶, "peer", g_strdup(file->fileown->name), GDestroyNotify(g_free)); addr.s_addr = file->fileown->ipv4; g_datalist_set_data_full(¶, "ip", g_strdup(inet_ntoa(addr)), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filename", ipmsg_get_filename_me(file->filepath, NULL), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(file->filesize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "finishlength", (gpointer)("0B")); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(0)); g_datalist_set_data(¶, "pro-text", (gpointer)("0.0%")); g_datalist_set_data(¶, "cost", (gpointer)("00:00:00")); g_datalist_set_data(¶, "remain", (gpointer)(_("unknown"))); g_datalist_set_data(¶, "rate", (gpointer)("0B/s")); g_datalist_set_data(¶, "filepath", file->filepath); g_datalist_set_data(¶, "data", this); } /** * 接收常规文件. */ void RecvFileData::RecvRegularFile() { AnalogFS afs; Command cmd; int64_t finishsize; int sock, fd; struct utimbuf timebuf; /* 创建文件传输套接口 */ if ((sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) { pop_error(_("Fatal Error!!\nFailed to create new socket!\n%s"), strerror(errno)); exit(1); } /* 请求文件数据 */ if (!cmd.SendAskData(sock, file->fileown, file->packetn, file->fileid, 0)) { close(sock); terminate = true; //标记处理过程失败 return; } /* 打开文件 */ if ((fd = afs.open(file->filepath, O_WRONLY | O_CREAT | O_TRUNC | O_LARGEFILE, 00644)) == -1) { close(sock); terminate = true; return; } /* 接收文件数据 */ gettimeofday(&filetime, NULL); finishsize = RecvData(sock, fd, file->filesize, 0); close(fd); if (file->filectime != 0) { timebuf.actime = int(file->filectime); timebuf.modtime = int(file->filectime); utime(file->filepath, &timebuf); } // sumsize += finishsize; /* 考察处理结果 */ if (finishsize < file->filesize) { terminate = true; g_lgsys->SystemLog(_("Failed to receive the file \"%s\" from %s!"), file->filepath, file->fileown->name); } else { g_lgsys->SystemLog(_("Receive the file \"%s\" from %s successfully!"), file->filepath, file->fileown->name); } /* 关闭文件传输套接口 */ close(sock); } /** * 接收目录文件. */ void RecvFileData::RecvDirFiles() { AnalogFS afs; Command cmd; gchar *dirname, *pathname, *filename, *filectime, *filemtime; int64_t filesize, finishsize; uint32_t headsize, fileattr; int sock, fd; ssize_t size; size_t len; bool result; struct utimbuf timebuf; /* 创建文件传输套接口 */ if ((sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) { pop_error(_("Fatal Error!!\nFailed to create new socket!\n%s"), strerror(errno)); exit(1); } /* 请求目录文件 */ if (!cmd.SendAskFiles(sock, file->fileown, file->packetn, file->fileid)) { close(sock); terminate = true; //标记处理过程失败 return; } /* 转到文件存档目录 */ g_free(ipmsg_get_filename_me(file->filepath, &pathname)); afs.mkdir(pathname, 0777); afs.chdir(pathname); g_free(pathname); /* 接收目录数据 */ result = false; //预设任务处理失败 len = 0; //预设缓冲区有效数据量为0 while (!terminate) { /* 读取足够的数据,并分析数据头 */ if ((size = read_ipmsg_fileinfo(sock, buf, MAX_SOCKLEN, len)) == -1) break; headsize = iptux_get_hex_number(buf, ':', 0); filename = ipmsg_get_filename(buf, ':', 1); filesize = iptux_get_hex64_number(buf, ':', 2); fileattr = iptux_get_hex_number(buf, ':', 3); filectime = iptux_get_section_string(buf, ':', 4); filemtime = iptux_get_section_string(buf, ':', 5); if (filectime != NULL) timebuf.actime = int(iptux_get_hex_number(filectime, '=', 1)); if (filemtime != NULL) timebuf.modtime = int(iptux_get_hex_number(filemtime, '=', 1)); len = size - headsize; //更新缓冲区有效数据量 /* 转码(如果好友不兼容iptux协议) */ if (!FLAG_ISSET(file->fileown->flags, 0) && strcasecmp(file->fileown->encode, "utf-8") != 0 && (dirname = convert_encode(filename, "utf-8", file->fileown->encode))) g_free(filename); else dirname = filename; /* 更新UI参考值 */ //要有谁敢在下一段代码中释放(dirname),那可别怪我没提醒哦 g_datalist_set_data_full(¶, "filename", dirname, GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(filesize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "finishlength", (gpointer)("0B")); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(0)); g_datalist_set_data(¶, "pro-text", (gpointer)("0.0%")); g_datalist_set_data(¶, "cost", (gpointer)("00:00:00")); g_datalist_set_data(¶, "remain", (gpointer)(_("unknown"))); g_datalist_set_data(¶, "rate", (gpointer)("0B/s")); /* 选择处理方案 */ gettimeofday(&filetime, NULL); switch (GET_MODE(fileattr)) { case IPMSG_FILE_RETPARENT: afs.chdir(".."); if (len) memmove(buf, buf + headsize, len); if (strlen(afs.cwd()) < strlen(file->filepath)) { //如果这时候还不成功结束就会陷入while开关第1句的死循环 result = true; goto end; } continue; case IPMSG_FILE_DIR: afs.mkdir(dirname, 0777); afs.chdir(dirname); if (len) memmove(buf, buf + headsize, len); continue; case IPMSG_FILE_REGULAR: if ((fd = afs.open(dirname, O_WRONLY | O_CREAT | O_TRUNC | O_LARGEFILE, 00644)) == -1) goto end; break; default: if ((fd = open("/dev/null", O_WRONLY)) == -1) goto end; break; } /* 处理缓冲区剩余数据&读取文件数据 */ size = len < filesize ? len : filesize; if (xwrite(fd, buf + headsize, size) == -1) { close(fd); goto end; } if (size == filesize) { //文件数据读取已完成 len -= size; if (len) memmove(buf, buf + headsize + size, len); finishsize = size; } else { //尚需继续读取文件数据 len = 0; //首先标记缓冲区已无有效数据 finishsize = RecvData(sock, fd, filesize, size); if (finishsize < filesize) { close(fd); goto end; } } close(fd); if (GET_MODE(fileattr) == IPMSG_FILE_REGULAR) { pathname = ipmsg_get_pathname_full(afs.cwd(), dirname); if (utime(pathname, &timebuf) < 0) g_print("Error to modify the file %s's filetime!\n", pathname); g_free(pathname); } // sumsize += filesize; } result = true; /* 考察处理结果 */ end: if (!result) { terminate = true; g_lgsys->SystemLog(_("Failed to receive the directory \"%s\" from %s!"), file->filepath, file->fileown->name); } else { g_lgsys->SystemLog(_("Receive the directory \"%s\" from %s successfully!"), file->filepath, file->fileown->name); } /* 关闭文件传输套接口 */ close(sock); } /** * 接收文件数据. * @param sock tcp socket * @param fd file descriptor * @param filesize 文件总长度 * @param offset 已读取数据量 * @return 完成数据量 */ int64_t RecvFileData::RecvData(int sock, int fd, int64_t filesize, int64_t offset) { int64_t tmpsize, finishsize; struct timeval val1, val2; float difftime, progress; uint32_t rate; ssize_t size; /* 如果文件数据已经完全被接收,则直接返回 */ if (offset == filesize) return filesize; /* 接收数据 */ tmpsize = finishsize = offset; //初始化已读取数据量 gettimeofday(&val1, NULL); //初始化起始时间 do { /* 接收数据并写入磁盘 */ size = MAX_SOCKLEN < filesize - finishsize ? MAX_SOCKLEN : filesize - finishsize; if ((size = xread(sock, buf, size)) == -1) return finishsize; if (size > 0 && xwrite(fd, buf, size) == -1) return finishsize; finishsize += size; sumsize += size; file->finishedsize = sumsize; /* 判断是否需要更新UI参考值 */ gettimeofday(&val2, NULL); difftime = difftimeval(val2, val1); if (difftime >= 1) { /* 更新UI参考值 */ progress = percent(finishsize, filesize); rate = (uint32_t)((finishsize - tmpsize) / difftime); g_datalist_set_data_full(¶, "finishlength", numeric_to_size(finishsize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(GINT(progress))); g_datalist_set_data_full(¶, "pro-text", g_strdup_printf("%.1f", progress), GDestroyNotify(g_free)); g_datalist_set_data_full( ¶, "cost", numeric_to_time((uint32_t)(difftimeval(val2, filetime))), GDestroyNotify(g_free)); g_datalist_set_data_full( ¶, "remain", numeric_to_time((uint32_t)((filesize - finishsize) / rate)), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "rate", numeric_to_rate(rate), GDestroyNotify(g_free)); // g_datalist_set_data_full(¶, "finishsize", // numeric_to_str(sumsize), // GDestroyNotify(g_free)); val1 = val2; //更新时间参考点 tmpsize = finishsize; //更新下载量 } } while (!terminate && size && finishsize < filesize); return finishsize; } /** * 更新UI参考数据到任务结束. */ void RecvFileData::UpdateUIParaToOver() { GtkIconTheme *theme; GdkPixbuf *pixbuf; struct timeval time; const char *statusfile; theme = gtk_icon_theme_get_default(); statusfile = terminate ? "tip-error" : "tip-finish"; if ((pixbuf = gtk_icon_theme_load_icon(theme, statusfile, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) g_datalist_set_data_full(¶, "status", pixbuf, GDestroyNotify(g_object_unref)); if (!terminate && GET_MODE(file->fileattr) == IPMSG_FILE_DIR) { g_datalist_set_data_full(¶, "filename", ipmsg_get_filename_me(file->filepath, NULL), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(sumsize), GDestroyNotify(g_free)); file->finishedsize = file->filesize; } if (!terminate) { gettimeofday(&time, NULL); g_datalist_set_data_full(¶, "finishlength", numeric_to_size(sumsize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(100)); g_datalist_set_data(¶, "pro-text", (gpointer)("100%")); g_datalist_set_data_full( ¶, "cost", numeric_to_time((uint32_t)(difftimeval(time, tasktime))), GDestroyNotify(g_free)); g_datalist_set_data(¶, "remain", NULL); g_datalist_set_data(¶, "rate", NULL); file->finishedsize = file->filesize; } g_datalist_set_data(¶, "data", NULL); } } // namespace iptuxiptux-0.7.4/src/iptux/RecvFileData.h000066400000000000000000000021541323207530100172730ustar00rootroot00000000000000// // C++ Interface: RecvFileData // // Description: // 接收文件数据 // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_RECVFILEDATA_H #define IPTUX_RECVFILEDATA_H #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class RecvFileData : public TransAbstract { public: RecvFileData(FileInfo *fl); ~RecvFileData(); void RecvFileDataEntry(); virtual GData **GetTransFilePara(); virtual void TerminateTrans(); private: void CreateUIPara(); void RecvRegularFile(); void RecvDirFiles(); int64_t RecvData(int sock, int fd, int64_t filesize, int64_t offset); void UpdateUIParaToOver(); FileInfo *file; //文件信息 GData *para; // UI参考数据 bool terminate; //终止标志(也作处理结果标识) int64_t sumsize; //文件(目录)总大小 char buf[MAX_SOCKLEN]; //数据缓冲区 struct timeval tasktime, filetime; //任务开始时间&文件开始时间 }; } // namespace iptux #endif iptux-0.7.4/src/iptux/RevisePal.cpp000066400000000000000000000311451323207530100172310ustar00rootroot00000000000000// // C++ Implementation: RevisePal // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "RevisePal.h" #include #include "iptux/CoreThread.h" #include "iptux/MainWindow.h" #include "iptux/callback.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/ipmsg.h" #include "iptux/utils.h" namespace iptux { /** * 类构造函数. * @param pl */ RevisePal::RevisePal(PalInfo *pl) : widset(NULL), mdlset(NULL), pal(pl) { InitSublayer(); } /** * 类析构函数. */ RevisePal::~RevisePal() { ClearSublayer(); } /** * 修正好友数据入口. * @param pal class PalInfo */ void RevisePal::ReviseEntry(PalInfo *pal) { RevisePal rpal(pal); GtkWidget *dialog; /* 创建对话框 */ dialog = rpal.CreateMainDialog(); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), rpal.CreateAllArea(), TRUE, TRUE, 0); rpal.SetAllValue(); /* 运行对话框 */ gtk_widget_show_all(dialog); switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_OK: rpal.ApplyReviseData(); break; default: break; } gtk_widget_destroy(dialog); } /** * 初始化底层数据. */ void RevisePal::InitSublayer() { GtkTreeModel *model; g_datalist_init(&widset); g_datalist_init(&mdlset); model = CreateIconModel(); g_datalist_set_data_full(&mdlset, "icon-model", model, GDestroyNotify(g_object_unref)); FillIconModel(model); } /** * 清空底层数据. */ void RevisePal::ClearSublayer() { g_datalist_clear(&widset); g_datalist_clear(&mdlset); } /** * 创建主对话框窗体. * @return 对话框 */ GtkWidget *RevisePal::CreateMainDialog() { GtkWidget *dialog; dialog = gtk_dialog_new_with_buttons( _("Change Pal's Information"), GTK_WINDOW(g_mwin->ObtainWindow()), GTK_DIALOG_MODAL, GTK_STOCK_OK, GTK_RESPONSE_OK, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); gtk_container_set_border_width(GTK_CONTAINER(dialog), 5); gtk_widget_set_size_request(dialog, 400, -1); g_datalist_set_data(&widset, "dialog-widget", dialog); return dialog; } /** * 创建所有区域窗体. * @return 主窗体 */ GtkWidget *RevisePal::CreateAllArea() { GtkWidget *box, *hbox; GtkWidget *label, *button, *widget; GtkTreeModel *model; box = gtk_vbox_new(FALSE, 0); /* 好友昵称 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Pal's nickname:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Please input pal's new nickname!")); g_datalist_set_data(&widset, "nickname-entry-widget", widget); /* 好友群组 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Pal's group name:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Please input pal's new group name!")); g_datalist_set_data(&widset, "group-entry-widget", widget); /* 好友系统编码 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("System coding:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); widget = gtk_entry_new(); g_object_set(widget, "has-tooltip", TRUE, NULL); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_signal_connect(widget, "query-tooltip", G_CALLBACK(entry_query_tooltip), _("Be SURE to know what you are doing!")); g_datalist_set_data(&widset, "encode-entry-widget", widget); /* 好友头像 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); label = gtk_label_new(_("Pal's face picture:")); gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "icon-model")); widget = CreateIconTree(model); gtk_box_pack_start(GTK_BOX(hbox), widget, TRUE, TRUE, 0); g_datalist_set_data(&widset, "icon-combo-widget", widget); button = gtk_button_new_with_label("..."); gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0); g_signal_connect(button, "clicked", G_CALLBACK(AddNewIcon), &widset); /* 协议兼容性 */ hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), hbox, FALSE, FALSE, 0); widget = gtk_check_button_new_with_label( _("Be compatible with iptux's protocol (DANGEROUS)")); gtk_box_pack_start(GTK_BOX(hbox), widget, FALSE, FALSE, 0); g_datalist_set_data(&widset, "compatible-check-widget", widget); return box; } /** * 给界面预设数据. */ void RevisePal::SetAllValue() { GtkWidget *widget; GtkTreeModel *model; gint active; /* 预置昵称 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "nickname-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), pal->name); /* 预置群组 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "group-entry-widget")); if (pal->group) gtk_entry_set_text(GTK_ENTRY(widget), pal->group); /* 预置编码 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "encode-entry-widget")); gtk_entry_set_text(GTK_ENTRY(widget), pal->encode); /* 预置头像 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "icon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = IconfileGetItemPos(model, pal->iconfile); gtk_combo_box_set_active(GTK_COMBO_BOX(widget), active); /* 预置兼容性 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "compatible-check-widget")); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), FLAG_ISSET(pal->flags, 0)); } /** * 应用修正后的数据. */ void RevisePal::ApplyReviseData() { GtkWidget *widget; GdkPixbuf *pixbuf; GtkTreeModel *model; GtkTreeIter iter; char path[MAX_PATHLEN]; gchar *text, *file; const gchar *consttext; gint active; /* 获取昵称 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "nickname-entry-widget")); if (*(consttext = gtk_entry_get_text(GTK_ENTRY(widget))) != '\0') { g_free(pal->name); pal->name = g_strdup(consttext); } /* 获取群组 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "group-entry-widget")); g_free(pal->group); if (*(consttext = gtk_entry_get_text(GTK_ENTRY(widget))) != '\0') pal->group = g_strdup(consttext); else pal->group = NULL; /* 获取编码 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "encode-entry-widget")); text = gtk_editable_get_chars(GTK_EDITABLE(widget), 0, -1); g_strstrip(text); if (*text != '\0') { g_free(pal->encode); pal->encode = text; } else g_free(text); /* 获取头像 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "icon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(widget)); active = gtk_combo_box_get_active(GTK_COMBO_BOX(widget)); snprintf(path, MAX_PATHLEN, "%d", active); gtk_tree_model_get_iter_from_string(model, &iter, path); gtk_tree_model_get(model, &iter, 1, &file, -1); if (strcmp(pal->iconfile, file) != 0) { snprintf(path, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", file); if (access(path, F_OK) != 0) { g_free(file); g_free(pal->iconfile); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/%" PRIx32, g_get_user_cache_dir(), pal->ipv4); pal->iconfile = g_strdup_printf("%" PRIx32, pal->ipv4); gtk_tree_model_get(model, &iter, 0, &pixbuf, -1); gdk_pixbuf_save(pixbuf, path, "png", NULL, NULL); gtk_icon_theme_add_builtin_icon(pal->iconfile, MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } else { g_free(pal->iconfile); pal->iconfile = file; } } else g_free(file); /* 获取兼容性 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "compatible-check-widget")); if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))) FLAG_SET(pal->flags, 0); else FLAG_CLR(pal->flags, 0); /* 设置好友信息已被手工修改 */ FLAG_SET(pal->flags, 2); /* 更新好友信息 */ g_cthrd->Lock(); g_cthrd->UpdatePalToList(pal->ipv4); g_cthrd->Unlock(); g_mwin->UpdateItemToPaltree(pal->ipv4); } /** * 头像树(icon-tree)底层数据结构. * 2,0 icon,1 iconfile \n * 头像;文件名(带后缀) \n * @return icon-model */ GtkTreeModel *RevisePal::CreateIconModel() { GtkListStore *model; model = gtk_list_store_new(2, GDK_TYPE_PIXBUF, G_TYPE_STRING); return GTK_TREE_MODEL(model); } /** * 为头像树(icon-tree)填充底层数据. * @param model icon-model */ void RevisePal::FillIconModel(GtkTreeModel *model) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkTreeIter iter; struct dirent *dirt; DIR *dir; char *file; theme = gtk_icon_theme_get_default(); if ((dir = opendir(__PIXMAPS_PATH "/icon"))) { while ((dirt = readdir(dir))) { if (strcmp(dirt->d_name, ".") == 0 || strcmp(dirt->d_name, "..") == 0) continue; file = iptux_erase_filename_suffix(dirt->d_name); if ((pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, dirt->d_name, -1); g_object_unref(pixbuf); } g_free(file); } closedir(dir); } } /** * 创建头像树(icon-tree). * @param model icon-model * @return 头像树 */ GtkWidget *RevisePal::CreateIconTree(GtkTreeModel *model) { GtkWidget *combo; GtkCellRenderer *cell; combo = gtk_combo_box_new_with_model(model); gtk_combo_box_set_wrap_width(GTK_COMBO_BOX(combo), 5); cell = gtk_cell_renderer_pixbuf_new(); gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(combo), cell, FALSE); gtk_cell_layout_set_attributes(GTK_CELL_LAYOUT(combo), cell, "pixbuf", 0, NULL); return combo; } /** * 查询(pathname)文件在(model)中的位置,若没有则加入到后面. * @param model model * @param pathname 文件路径 * @return 位置 */ gint RevisePal::IconfileGetItemPos(GtkTreeModel *model, const char *pathname) { GtkIconTheme *theme; GdkPixbuf *pixbuf; GtkTreeIter iter; const char *ptr; gchar *file; gint result, pos; /* 让ptr指向文件名 */ ptr = strrchr(pathname, '/'); ptr = ptr ? ptr + 1 : pathname; /* 查询model中是否已经存在此文件 */ pos = 0; if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, 1, &file, -1); result = strcmp(ptr, file); g_free(file); if (result == 0) return pos; pos++; } while (gtk_tree_model_iter_next(model, &iter)); } /* 将文件加入model */ if (access(pathname, F_OK) != 0) { theme = gtk_icon_theme_get_default(); file = iptux_erase_filename_suffix(pathname); pixbuf = gtk_icon_theme_load_icon(theme, file, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL); g_free(file); } else pixbuf = gdk_pixbuf_new_from_file_at_size(pathname, MAX_ICONSIZE, MAX_ICONSIZE, NULL); if (pixbuf) { gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, ptr, -1); g_object_unref(pixbuf); } else pos = -1; return pos; } /** * 添加新的头像数据. * @param button button * @param widset widget set */ void RevisePal::AddNewIcon(GtkWidget *button, GData **widset) { GtkWidget *parent, *combo; GtkTreeModel *model; gchar *filename; gint active; parent = GTK_WIDGET(g_datalist_get_data(widset, "dialog-widget")); if (!(filename = choose_file_with_preview(_("Please select a face picture"), parent))) return; combo = GTK_WIDGET(g_object_get_data(G_OBJECT(button), "icon-combo-widget")); model = gtk_combo_box_get_model(GTK_COMBO_BOX(combo)); active = IconfileGetItemPos(model, filename); gtk_combo_box_set_active(GTK_COMBO_BOX(combo), active); g_free(filename); } } // namespace iptux iptux-0.7.4/src/iptux/RevisePal.h000066400000000000000000000017141323207530100166750ustar00rootroot00000000000000// // C++ Interface: RevisePal // // Description:手动更改好友数据 // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_REVISEPAL_H #define IPTUX_REVISEPAL_H #include "iptux/mess.h" namespace iptux { class RevisePal { public: RevisePal(PalInfo *pl); ~RevisePal(); static void ReviseEntry(PalInfo *pal); private: void InitSublayer(); void ClearSublayer(); GtkWidget *CreateMainDialog(); GtkWidget *CreateAllArea(); void SetAllValue(); void ApplyReviseData(); GtkTreeModel *CreateIconModel(); void FillIconModel(GtkTreeModel *model); GtkWidget *CreateIconTree(GtkTreeModel *model); GData *widset; GData *mdlset; PalInfo *pal; private: static gint IconfileGetItemPos(GtkTreeModel *model, const char *pathname); //回调处理部分 private: static void AddNewIcon(GtkWidget *button, GData **widset); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/SendFile.cpp000066400000000000000000000125711323207530100170320ustar00rootroot00000000000000// // C++ Implementation: SendFile // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "SendFile.h" #include #include #include "iptux/AnalogFS.h" #include "iptux/Command.h" #include "iptux/CoreThread.h" #include "iptux/SendFileData.h" #include "iptux/global.h" #include "iptux/utils.h" namespace iptux { SendFile::SendFile() {} SendFile::~SendFile() {} /** * 发送本机共享文件信息入口. * @param pal class PalInfo */ void SendFile::SendSharedInfoEntry(PalInfo *pal) { GSList *list; g_cthrd->Lock(); list = g_cthrd->GetPublicFileList(); SendFileInfo(pal, IPTUX_SHAREDOPT, list); g_cthrd->Unlock(); } /** * 发送文件信息入口. * @param pal class PalInfo * @param flist 文件信息链表 * @note 文件路径链表中的数据将被本函数处理掉 */ void SendFile::SendFileInfoEntry(PalInfo *pal, GSList *flist) { /* 发送文件信息 */ SendFileInfo(pal, 0, flist); } /** * 广播文件信息入口. * @param plist 好友链表 * @param flist 文件信息链表 * @note 文件路径链表中的数据将被本函数处理掉 */ void SendFile::BcstFileInfoEntry(GSList *plist, GSList *flist) { BcstFileInfo(plist, 0, flist); } /** * 请求文件数据入口. * @param sock tcp socket * @param fileattr 文件类型 * @param attach 附加数据 */ void SendFile::RequestDataEntry(int sock, uint32_t fileattr, char *attach) { struct sockaddr_in addr; socklen_t len; PalInfo *pal; FileInfo *file; uint32_t fileid; uint32_t filectime; /* 检查文件属性是否匹配 */ fileid = iptux_get_hex_number(attach, ':', 1); file = (FileInfo *)g_cthrd->GetFileFromAll(fileid); /* 兼容windows版信鸽(IPMSG) ,这里的信鸽不是飞鸽传书(IPMSG)*/ if (!file) { fileid = iptux_get_dec_number(attach, ':', 1); file = (FileInfo *)g_cthrd->GetFileFromAll(fileid); } /* 兼容adroid版信鸽(IPMSG) */ if (!file) { fileid = iptux_get_hex_number(attach, ':', 0); filectime = iptux_get_dec_number(attach, ':', 1); file = (FileInfo *)g_cthrd->GetFileFromAllWithPacketN(fileid, filectime); } if (!file || GET_MODE(file->fileattr) != GET_MODE(fileattr)) return; /* 检查好友数据是否存在 */ len = sizeof(addr); getpeername(sock, (struct sockaddr *)&addr, &len); if (!(pal = g_cthrd->GetPalFromList(addr.sin_addr.s_addr))) return; /* 发送文件数据 */ // /** // *文件信息可能被删除或修改,必须单独复制一份. // */ // file->fileown = pal; ThreadSendFile(sock, file); } /** * 发送文件信息. * @param pal class PalInfo * @param opttype 命令字选项 * @param filist 文件信息链表 */ void SendFile::SendFileInfo(PalInfo *pal, uint32_t opttype, GSList *filist) { AnalogFS afs; Command cmd; char buf[MAX_UDPLEN]; size_t len; char *ptr, *name; GSList *tlist; FileInfo *file; /* 初始化 */ len = 0; ptr = buf; buf[0] = '\0'; /* 将文件信息写入缓冲区 */ tlist = filist; while (tlist) { file = (FileInfo *)tlist->data; if (access(file->filepath, F_OK) == -1) { tlist = g_slist_next(tlist); continue; } name = ipmsg_get_filename_pal(file->filepath); //获取面向好友的文件名 file->packetn = cmd.Packetn(); snprintf(ptr, MAX_UDPLEN - len, "%" PRIu32 ":%s:%" PRIx64 ":%" PRIx32 ":%" PRIx32 ":\a", file->fileid, name, file->filesize, file->filectime, file->fileattr); g_free(name); len += strlen(ptr); ptr = buf + len; tlist = g_slist_next(tlist); } /* 发送文件信息 */ cmd.SendFileInfo(g_cthrd->UdpSockQuote(), pal, opttype, buf); } /** * 广播文件信息. * @param plist 好友链表 * @param opttype 命令字选项 * @param filist 文件信息链表 */ void SendFile::BcstFileInfo(GSList *plist, uint32_t opttype, GSList *filist) { AnalogFS afs; Command cmd; char buf[MAX_UDPLEN]; size_t len; char *ptr, *name; GSList *pallist, *filelist; FileInfo *file; /* 初始化 */ len = 0; ptr = buf; buf[0] = '\0'; pallist = plist; /* 将文件信息写入缓冲区 */ while (pallist) { filelist = filist; while (filelist) { file = (FileInfo *)filelist->data; if (file->fileown == (PalInfo *)pallist->data) { if (access(file->filepath, F_OK) == -1) { filelist = g_slist_next(filelist); continue; } name = ipmsg_get_filename_pal(file->filepath); //获取面向好友的文件名 file->filesize = afs.ftwsize(file->filepath); //不得不计算文件长度了 file->packetn = cmd.Packetn(); snprintf(ptr, MAX_UDPLEN - len, "%" PRIu32 ":%s:%" PRIx64 ":%" PRIx32 ":%" PRIx32 ":\a:", file->fileid, name, file->filesize, file->filectime, file->fileattr); g_free(name); len += strlen(ptr); ptr = buf + len; } filelist = g_slist_next(filelist); } cmd.SendFileInfo(g_cthrd->UdpSockQuote(), (PalInfo *)pallist->data, opttype, buf); pallist = g_slist_next(pallist); } } /** * 发送文件数据. * @param sock tcp socket * @param file 文件信息 */ void SendFile::ThreadSendFile(int sock, FileInfo *file) { SendFileData sfdt(sock, file); sfdt.SendFileDataEntry(); } } // namespace iptuxiptux-0.7.4/src/iptux/SendFile.h000066400000000000000000000014741323207530100164770ustar00rootroot00000000000000// // C++ Interface: SendFile // // Description: // 发送相关的文件信息,不包含文件数据 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_SENDFILE_H #define IPTUX_SENDFILE_H #include "iptux/mess.h" namespace iptux { class SendFile { public: SendFile(); ~SendFile(); void SendSharedInfoEntry(PalInfo *pal); void SendFileInfoEntry(PalInfo *pal, GSList *flist); void BcstFileInfoEntry(GSList *plist, GSList *flist); void RequestDataEntry(int sock, uint32_t fileattr, char *attach); private: void SendFileInfo(PalInfo *pal, uint32_t opttype, GSList *filist); void BcstFileInfo(GSList *plist, uint32_t opttype, GSList *filist); void ThreadSendFile(int sock, FileInfo *file); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/SendFileData.cpp000066400000000000000000000305431323207530100176230ustar00rootroot00000000000000// // C++ Implementation: SendFileData // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "SendFileData.h" #include #include #include #include #include #include #include #include "iptux/AnalogFS.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/utils.h" #include "iptux/wrapper.h" namespace iptux { /** * 类构造函数. * @param sk tcp socket * @param fl 文件信息数据 */ SendFileData::SendFileData(int sk, FileInfo *fl) : sock(sk), file(fl), para(NULL), terminate(false), sumsize(0) { g_datalist_init(¶); gettimeofday(&tasktime, NULL); /* gettimeofday(&filetime, NULL);//个人感觉没必要 */ } /** * 类析构函数. */ SendFileData::~SendFileData() { g_datalist_clear(¶); } /** * 发送文件数据入口. */ void SendFileData::SendFileDataEntry() { /* 创建UI参考数据,并将数据主动加入UI */ gdk_threads_enter(); CreateUIPara(); g_mwin->UpdateItemToTransTree(¶); if (g_progdt->IsAutoOpenFileTrans()) { g_mwin->OpenTransWindow(); } gdk_threads_leave(); /* 分类处理 */ switch (GET_MODE(file->fileattr)) { case IPMSG_FILE_REGULAR: SendRegularFile(); break; case IPMSG_FILE_DIR: SendDirFiles(); break; default: break; } /* 主动更新UI */ gdk_threads_enter(); UpdateUIParaToOver(); g_mwin->UpdateItemToTransTree(¶); gdk_threads_leave(); /* 处理成功则播放提示音 */ if (!terminate && FLAG_ISSET(g_progdt->sndfgs, 2)) g_sndsys->Playing(g_progdt->transtip); } /** * 获取UI参考数据. * @return UI参考数据 */ GData **SendFileData::GetTransFilePara() { return ¶ } /** * 终止过程处理. */ void SendFileData::TerminateTrans() { terminate = true; } /** * 创建UI参考数据. */ void SendFileData::CreateUIPara() { GtkIconTheme *theme; GdkPixbuf *pixbuf; struct in_addr addr; theme = gtk_icon_theme_get_default(); if ((pixbuf = gtk_icon_theme_load_icon(theme, "tip-send", MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) g_datalist_set_data_full(¶, "status", pixbuf, GDestroyNotify(g_object_unref)); g_datalist_set_data(¶, "task", (gpointer)(_("send"))); g_datalist_set_data_full(¶, "peer", g_strdup(file->fileown->name), GDestroyNotify(g_free)); addr.s_addr = file->fileown->ipv4; g_datalist_set_data_full(¶, "ip", g_strdup(inet_ntoa(addr)), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filename", ipmsg_get_filename_me(file->filepath, NULL), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(file->filesize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "finishlength", (gpointer)("0B")); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(0)); g_datalist_set_data(¶, "pro-text", (gpointer)("0.0%")); g_datalist_set_data(¶, "cost", (gpointer)("00:00:00")); g_datalist_set_data(¶, "remain", (gpointer)(_("unknown"))); g_datalist_set_data(¶, "rate", (gpointer)("0B/s")); g_datalist_set_data(¶, "data", this); } /** * 发送常规文件. */ void SendFileData::SendRegularFile() { int64_t finishsize; int fd; /* 打开文件 */ if ((fd = open(file->filepath, O_RDONLY | O_LARGEFILE)) == -1) { terminate = true; //标记处理过程失败 return; } /* 发送文件数据 */ gettimeofday(&filetime, NULL); finishsize = SendData(fd, file->filesize); close(fd); // sumsize += finishsize; /* 考察处理结果 */ if (finishsize < file->filesize) { terminate = true; g_lgsys->SystemLog(_("Failed to send the file \"%s\" to %s!"), file->filepath, file->fileown->name); } else { g_lgsys->SystemLog(_("Send the file \"%s\" to %s successfully!"), file->filepath, file->fileown->name); } } /** * 发送目录文件. */ void SendFileData::SendDirFiles() { AnalogFS afs; GQueue dirstack = G_QUEUE_INIT; struct stat st; struct dirent *dirt, vdirt; DIR *dir; gchar *dirname, *pathname, *filename; int64_t finishsize; uint32_t headsize; int fd; bool result; /* 转到上传目录位置 */ dirname = ipmsg_get_filename_me(file->filepath, &pathname); afs.chdir(pathname); g_free(pathname); strcpy(vdirt.d_name, dirname); dirt = &vdirt; g_free(dirname); result = false; //预设任务处理失败 dir = NULL; //预设当前目录流无效 goto start; while (!g_queue_is_empty(&dirstack)) { /* 取出最后一次压入堆栈的目录流 */ dir = (DIR *)g_queue_pop_head(&dirstack); /* 发送目录流中的下属数据 */ while (dir && (dirt = readdir(dir))) { if (strcmp(dirt->d_name, ".") == 0 || strcmp(dirt->d_name, "..") == 0) continue; /* 检查文件是否可用 */ start: if (afs.stat(dirt->d_name, &st) == -1 || !(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode))) continue; /* 更新UI参考值 */ g_datalist_set_data_full(¶, "filename", g_strdup(dirt->d_name), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(st.st_size), GDestroyNotify(g_free)); g_datalist_set_data(¶, "finishlength", (gpointer)("0B")); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(0)); g_datalist_set_data(¶, "pro-text", (gpointer)("0.0%")); g_datalist_set_data(¶, "cost", (gpointer)("00:00:00")); g_datalist_set_data(¶, "remain", (gpointer)(_("unknown"))); g_datalist_set_data(¶, "rate", (gpointer)("0B/s")); /* 转码 */ if (strcasecmp(file->fileown->encode, "utf-8") != 0 && (filename = convert_encode(dirt->d_name, file->fileown->encode, "utf-8"))) { dirname = ipmsg_get_filename_pal(filename); g_free(filename); } else dirname = ipmsg_get_filename_pal(dirt->d_name); /* 构造数据头并发送 */ snprintf(buf, MAX_SOCKLEN, "0000:%s:%.9" PRIx64 ":%lx:%lx=%lx:%lx=%lx:", dirname, S_ISREG(st.st_mode) ? st.st_size : 0, S_ISREG(st.st_mode) ? IPMSG_FILE_REGULAR : IPMSG_FILE_DIR, IPMSG_FILE_MTIME, st.st_mtime, IPMSG_FILE_CREATETIME, st.st_ctime); g_free(dirname); headsize = strlen(buf); snprintf(buf, MAX_SOCKLEN, "%.4" PRIx32, headsize); *(buf + 4) = ':'; if (xwrite(sock, buf, headsize) == -1) goto end; /* 选择处理方案 */ gettimeofday(&filetime, NULL); if (S_ISREG(st.st_mode)) { //常规文件 if ((fd = afs.open(dirt->d_name, O_RDONLY | O_LARGEFILE)) == -1) goto end; finishsize = SendData(fd, st.st_size); close(fd); if (finishsize < st.st_size) goto end; // sumsize += finishsize; } else if (S_ISDIR(st.st_mode)) { //目录文件 if (dir) //若当前目录流有效则须压入堆栈 g_queue_push_head(&dirstack, dir); /* 打开下属目录 */ if (!(dir = afs.opendir(dirt->d_name))) goto end; /* 本地端也须转至下属目录 */ afs.chdir(dirt->d_name); } } /* 目录流有效才可向上转 */ if (dir) { /* 关闭当前操作的目录流 */ closedir(dir); dir = NULL; /* 构造向上转的数据头并发送 */ snprintf(buf, MAX_SOCKLEN, "0000:.:0:%lx:%lx=%lx:%lx=%lx:", IPMSG_FILE_RETPARENT, IPMSG_FILE_MTIME, st.st_mtime, IPMSG_FILE_CREATETIME, st.st_ctime); headsize = strlen(buf); snprintf(buf, MAX_SOCKLEN, "%.4" PRIx32, headsize); *(buf + 4) = ':'; if (xwrite(sock, buf, headsize) == -1) goto end; /* 本地端也须向上转一层 */ afs.chdir(".."); } } result = true; /* 考察处理结果 */ end: if (!result) { /* 若当前目录流有效,则必须关闭 */ if (dir) closedir(dir); /* 关闭堆栈中所有的目录流,并清空堆栈 */ g_queue_foreach(&dirstack, GFunc(closedir), NULL); g_queue_clear(&dirstack); g_lgsys->SystemLog(_("Failed to send the directory \"%s\" to %s!"), file->filepath, file->fileown->name); } else { g_lgsys->SystemLog(_("Send the directory \"%s\" to %s successfully!"), file->filepath, file->fileown->name); } } /** * 发送文件数据. * @param fd file descriptor * @param filesize 文件总长度 * @return 完成数据量 */ int64_t SendFileData::SendData(int fd, int64_t filesize) { int64_t tmpsize, finishsize; struct timeval val1, val2; float difftime, progress; uint32_t rate; ssize_t size; /* 如果文件长度为0,则无须再进一步处理 */ if (filesize == 0) return 0; tmpsize = finishsize = 0; //初始化已完成数据量 gettimeofday(&val1, NULL); //初始化起始时间 do { /* 读取文件数据并发送 */ size = MAX_SOCKLEN < filesize - finishsize ? MAX_SOCKLEN : filesize - finishsize; if ((size = xread(fd, buf, MAX_SOCKLEN)) == -1) return finishsize; if (size > 0 && xwrite(sock, buf, size) == -1) return finishsize; finishsize += size; sumsize += size; file->finishedsize = sumsize; /* 判断是否需要更新UI参考值 */ gettimeofday(&val2, NULL); difftime = difftimeval(val2, val1); if (difftime >= 1) { /* 更新UI参考值 */ progress = percent(finishsize, filesize); rate = (uint32_t)((finishsize - tmpsize) / difftime); g_datalist_set_data_full(¶, "finishlength", numeric_to_size(finishsize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(GINT(progress))); g_datalist_set_data_full(¶, "pro-text", g_strdup_printf("%.1f", progress), GDestroyNotify(g_free)); g_datalist_set_data_full( ¶, "cost", numeric_to_time((uint32_t)(difftimeval(val2, filetime))), GDestroyNotify(g_free)); g_datalist_set_data_full( ¶, "remain", numeric_to_time((uint32_t)((filesize - finishsize) / rate)), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "rate", numeric_to_rate(rate), GDestroyNotify(g_free)); val1 = val2; //更新时间参考点 tmpsize = finishsize; //更新下载量 } } while (!terminate && size && finishsize < filesize); return finishsize; } /** * 更新UI参考数据到任务结束. */ void SendFileData::UpdateUIParaToOver() { GtkIconTheme *theme; GdkPixbuf *pixbuf; struct timeval time; const char *statusfile; theme = gtk_icon_theme_get_default(); statusfile = terminate ? "tip-error" : "tip-finish"; if ((pixbuf = gtk_icon_theme_load_icon(theme, statusfile, MAX_ICONSIZE, GtkIconLookupFlags(0), NULL))) g_datalist_set_data_full(¶, "status", pixbuf, GDestroyNotify(g_object_unref)); if (!terminate && GET_MODE(file->fileattr) == IPMSG_FILE_DIR) { g_datalist_set_data_full(¶, "filename", ipmsg_get_filename_me(file->filepath, NULL), GDestroyNotify(g_free)); g_datalist_set_data_full(¶, "filelength", numeric_to_size(sumsize), GDestroyNotify(g_free)); } if (!terminate) { gettimeofday(&time, NULL); g_datalist_set_data_full(¶, "finishlength", numeric_to_size(sumsize), GDestroyNotify(g_free)); g_datalist_set_data(¶, "progress", GINT_TO_POINTER(100)); g_datalist_set_data(¶, "pro-text", (gpointer)("100%")); g_datalist_set_data_full( ¶, "cost", numeric_to_time((uint32_t)(difftimeval(time, tasktime))), GDestroyNotify(g_free)); g_datalist_set_data(¶, "remain", NULL); g_datalist_set_data(¶, "rate", NULL); } g_datalist_set_data(¶, "data", NULL); } } // namespace iptux iptux-0.7.4/src/iptux/SendFileData.h000066400000000000000000000022221323207530100172610ustar00rootroot00000000000000// // C++ Interface: SendFileData // // Description: // 发送文件数据 // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_SENDFILEDATA_H #define IPTUX_SENDFILEDATA_H #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class SendFileData : public TransAbstract { public: SendFileData(int sk, FileInfo *fl); ~SendFileData(); void SendFileDataEntry(); virtual GData **GetTransFilePara(); virtual void TerminateTrans(); private: void CreateUIPara(); void SendRegularFile(); void SendDirFiles(); int64_t SendData(int fd, int64_t filesize); void UpdateUIParaToOver(); int sock; //数据套接口 FileInfo *file; //文件信息 GData *para; // UI参考数据 bool terminate; //终止标志(也作处理结果标识) int64_t sumsize; //文件(目录)总大小 char buf[MAX_SOCKLEN]; //数据缓冲区 struct timeval tasktime, filetime; //任务开始时间&文件开始时间 }; } // namespace iptux #endif iptux-0.7.4/src/iptux/ShareFile.cpp000066400000000000000000000411351323207530100172010ustar00rootroot00000000000000// // C++ Implementation: ShareFile // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "ShareFile.h" #include #include "iptux/AnalogFS.h" #include "iptux/deplib.h" #include "iptux/dialog.h" #include "iptux/global.h" #include "iptux/support.h" #include "iptux/utils.h" namespace iptux { /** * 类构造函数. */ ShareFile::ShareFile() : widset(NULL), mdlset(NULL) { InitSublayer(); } /** * 类析构函数. */ ShareFile::~ShareFile() { ClearSublayer(); } /** * 共享文件浏览、更新入口. * @param parent 父窗口指针 */ void ShareFile::ShareEntry(GtkWidget *parent) { ShareFile sfile; GtkWidget *dialog; /* 创建对话框 */ dialog = sfile.CreateMainDialog(parent); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), sfile.CreateAllArea(), TRUE, TRUE, 0); /* 运行对话框 */ gtk_widget_show_all(dialog); mark: switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_OK: sfile.ApplySharedData(); break; case GTK_RESPONSE_APPLY: sfile.ApplySharedData(); goto mark; case GTK_RESPONSE_CANCEL: default: break; } gtk_widget_destroy(dialog); } /** * 初始化底层数据. */ void ShareFile::InitSublayer() { GtkTreeModel *model; g_datalist_init(&widset); g_datalist_init(&mdlset); model = CreateFileModel(); g_datalist_set_data_full(&mdlset, "file-model", model, GDestroyNotify(g_object_unref)); FillFileModel(model); } /** * 清空底层数据. */ void ShareFile::ClearSublayer() { g_datalist_clear(&widset); g_datalist_clear(&mdlset); } /** * 创建主对话框窗口. * @param parent 父窗口指针 * @return 对话框 */ GtkWidget *ShareFile::CreateMainDialog(GtkWidget *parent) { GtkWidget *dialog; dialog = gtk_dialog_new_with_buttons( _("Shared Files Management"), GTK_WINDOW(parent), GtkDialogFlags(GTK_DIALOG_MODAL), _("OK"), GTK_RESPONSE_OK, _("Apply"), GTK_RESPONSE_APPLY, _("Cancel"), GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); gtk_window_set_position(GTK_WINDOW(dialog), GTK_WIN_POS_CENTER); gtk_container_set_border_width(GTK_CONTAINER(dialog), 5); gtk_widget_set_size_request(dialog, 500, 350); g_datalist_set_data(&widset, "dialog-widget", dialog); widget_enable_dnd_uri(dialog); g_signal_connect_swapped(dialog, "drag-data-received", G_CALLBACK(DragDataReceived), this); return dialog; } /** * 创建对话框中所有的窗体. * @return 主窗体 */ GtkWidget *ShareFile::CreateAllArea() { GtkWidget *box, *vbox; GtkWidget *sw, *button, *widget; GtkTreeModel *model; box = gtk_hbox_new(FALSE, 0); /* 加入文件树 */ sw = gtk_scrolled_window_new(NULL, NULL); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_ETCHED_IN); gtk_box_pack_end(GTK_BOX(box), sw, TRUE, TRUE, 0); model = GTK_TREE_MODEL(g_datalist_get_data(&mdlset, "file-model")); widget = CreateFileTree(model); gtk_container_add(GTK_CONTAINER(sw), widget); g_datalist_set_data(&widset, "file-treeview-widget", widget); /* 加入N多垃圾按钮 */ vbox = gtk_vbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(box), vbox, FALSE, FALSE, 0); button = gtk_button_new_with_label(_("Add Files")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(AddRegular), this); button = gtk_button_new_with_label(_("Add Folders")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(AddFolder), this); button = gtk_button_new_with_label(_("Delete Resources")); gtk_box_pack_start(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(DeleteFiles), &widset); button = gtk_button_new_with_label(_("Clear Password")); gtk_box_pack_end(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(ClearPassword), &widset); button = gtk_button_new_with_label(_("Set Password")); gtk_box_pack_end(GTK_BOX(vbox), button, FALSE, FALSE, 0); g_signal_connect_swapped(button, "clicked", G_CALLBACK(SetPassword), &widset); g_datalist_set_data(&widset, "password-button-widget", button); return box; } /** * 文件树(file-tree)底层数据结构. * 5,0 logo,1 filepath,2 filesize,3 filetype,4 type * 文件图标;文件路径;文件大小;文件类型(串);文件类型(数值) * @return file-model */ GtkTreeModel *ShareFile::CreateFileModel() { GtkListStore *model; model = gtk_list_store_new(5, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_UINT); gtk_tree_sortable_set_default_sort_func( GTK_TREE_SORTABLE(model), GtkTreeIterCompareFunc(FileTreeCompareFunc), NULL, NULL); gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); return GTK_TREE_MODEL(model); } /** * 为文件树(file-tree)填充底层数据. * @param model file-model */ void ShareFile::FillFileModel(GtkTreeModel *model) { AnalogFS afs; GdkPixbuf *pixbuf, *rpixbuf, *dpixbuf; GtkTreeIter iter; char *filesize; const char *filetype; FileInfo *file; GSList *tlist; /* 先获取两个文件图标 */ rpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_FILE); dpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_DIRECTORY); /* 将现在的共享文件填入model */ tlist = g_cthrd->GetPublicFileList(); while (tlist) { file = (FileInfo *)tlist->data; /* 获取文件大小 */ file->filesize = afs.ftwsize(file->filepath); filesize = numeric_to_size(file->filesize); /* 获取文件类型 */ switch (GET_MODE(file->fileattr)) { case IPMSG_FILE_REGULAR: filetype = _("regular"); pixbuf = rpixbuf; break; case IPMSG_FILE_DIR: filetype = _("directory"); pixbuf = dpixbuf; break; default: filetype = _("unknown"); pixbuf = NULL; break; } /* 填入数据 */ gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, file->filepath, 2, filesize, 3, filetype, 4, file->fileattr, -1); /* 烦,释放资源 */ g_free(filesize); /* 转入下一个节点 */ tlist = g_slist_next(tlist); } /* 释放文件图标 */ if (rpixbuf) g_object_unref(rpixbuf); if (dpixbuf) g_object_unref(dpixbuf); } /** * 创建文件树(file-tree). * @param model file-model * @return 文件树 */ GtkWidget *ShareFile::CreateFileTree(GtkTreeModel *model) { GtkWidget *view; GtkTreeViewColumn *column; GtkCellRenderer *cell; GtkTreeSelection *selection; view = gtk_tree_view_new_with_model(model); gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), TRUE); gtk_tree_view_set_rubber_banding(GTK_TREE_VIEW(view), TRUE); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view)); gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE); column = gtk_tree_view_column_new(); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_column_set_title(column, _("File")); cell = gtk_cell_renderer_pixbuf_new(); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "pixbuf", 0, NULL); cell = gtk_cell_renderer_text_new(); gtk_tree_view_column_pack_start(column, cell, FALSE); gtk_tree_view_column_set_attributes(column, cell, "text", 1, NULL); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Size"), cell, "text", 2, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); cell = gtk_cell_renderer_text_new(); column = gtk_tree_view_column_new_with_attributes(_("Type"), cell, "text", 3, NULL); gtk_tree_view_column_set_resizable(column, TRUE); gtk_tree_view_append_column(GTK_TREE_VIEW(view), column); return view; } /** * 应用共享文件数据. */ void ShareFile::ApplySharedData() { GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; FileInfo *file; uint32_t fileattr; gchar *filepath; const gchar *passwd; AnalogFS afs; struct stat st; /* 更新共享文件链表 */ g_cthrd->Lock(); g_cthrd->ClearFileFromPublic(); g_cthrd->PbnQuote() = 1; widget = GTK_WIDGET(g_datalist_get_data(&widset, "file-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (gtk_tree_model_get_iter_first(model, &iter)) { do { gtk_tree_model_get(model, &iter, 1, &filepath, 4, &fileattr, -1); file = new FileInfo; file->fileid = g_cthrd->PbnQuote()++; /* file->packetn = 0;//没必要设置此字段 */ file->fileattr = fileattr; /* file->filesize = 0;//我喜欢延后处理 */ /* file->fileown = NULL;//没必要设置此字段 */ file->filepath = filepath; if (afs.stat(filepath, &st) == 0) file->filectime = st.st_ctime; g_cthrd->AttachFileToPublic(file); } while (gtk_tree_model_iter_next(model, &iter)); } g_cthrd->Unlock(); /* 更新密码 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "password-button-widget")); passwd = (const gchar *)g_object_get_data(G_OBJECT(widget), "password"); g_cthrd->SetAccessPublicLimit(passwd); /* 写出共享文件 */ g_cthrd->WriteSharedData(); } /** * 增加新的共享文件. * @param list 文件链表 */ void ShareFile::AttachSharedFiles(GSList *list) { AnalogFS afs; GtkWidget *widget; GtkTreeModel *model; GtkTreeIter iter; GdkPixbuf *pixbuf, *rpixbuf, *dpixbuf; struct stat st; int64_t pathsize; GSList *tlist; char *filesize; const char *filetype; uint32_t fileattr; /* 获取文件图标 */ rpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_FILE); dpixbuf = obtain_pixbuf_from_stock(GTK_STOCK_DIRECTORY); /* 插入文件树 */ widget = GTK_WIDGET(g_datalist_get_data(&widset, "file-treeview-widget")); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); tlist = list; while (tlist) { if (stat((const char *)tlist->data, &st) == -1 || !(S_ISREG(st.st_mode) || S_ISDIR(st.st_mode))) { tlist = g_slist_next(tlist); continue; } /* 获取文件大小 */ pathsize = afs.ftwsize((const char *)tlist->data); filesize = numeric_to_size(pathsize); /* 获取文件类型 */ if (S_ISREG(st.st_mode)) { filetype = _("regular"); fileattr = IPMSG_FILE_REGULAR; pixbuf = rpixbuf; } else if (S_ISDIR(st.st_mode)) { filetype = _("directory"); fileattr = IPMSG_FILE_DIR; pixbuf = dpixbuf; } else { filetype = _("unknown"); fileattr = 0; pixbuf = NULL; } /* 添加数据 */ gtk_list_store_append(GTK_LIST_STORE(model), &iter); gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, pixbuf, 1, tlist->data, 2, filesize, 3, filetype, 4, fileattr, -1); /* 释放资源 */ g_free(filesize); /* 转到下一个节点 */ tlist = g_slist_next(tlist); } /* 释放文件图标 */ if (rpixbuf) g_object_unref(rpixbuf); if (dpixbuf) g_object_unref(dpixbuf); } /** * 选择新的共享文件. * @param fileattr 文件类型 * @return 文件链表 */ GSList *ShareFile::PickSharedFile(uint32_t fileattr) { GtkWidget *dialog, *parent; GtkFileChooserAction action; const char *title; GSList *list; if (GET_MODE(fileattr) == IPMSG_FILE_REGULAR) { action = GTK_FILE_CHOOSER_ACTION_OPEN; title = _("Choose the files to share"); } else { action = GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER; title = _("Choose the folders to share"); } parent = GTK_WIDGET(g_datalist_get_data(&widset, "dialog-widget")); dialog = gtk_file_chooser_dialog_new( title, GTK_WINDOW(parent), action, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(dialog), FALSE); gtk_file_chooser_set_select_multiple(GTK_FILE_CHOOSER(dialog), TRUE); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog), g_get_home_dir()); switch (gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_ACCEPT: list = gtk_file_chooser_get_filenames(GTK_FILE_CHOOSER(dialog)); break; case GTK_RESPONSE_CANCEL: default: list = NULL; break; } gtk_widget_destroy(dialog); return list; } /** * 增添常规文件. * @param sfile 共享文件类 */ void ShareFile::AddRegular(ShareFile *sfile) { GSList *list; list = sfile->PickSharedFile(IPMSG_FILE_REGULAR); sfile->AttachSharedFiles(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); } /** * 增添目录文件. * @param sfile 共享文件类 */ void ShareFile::AddFolder(ShareFile *sfile) { GSList *list; list = sfile->PickSharedFile(IPMSG_FILE_DIR); sfile->AttachSharedFiles(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); } /** * 删除被选中的共享文件. * @param widset widget set */ void ShareFile::DeleteFiles(GData **widset) { GtkWidget *widget; GtkTreeSelection *selection; GtkTreeModel *model; GtkTreeIter iter; widget = GTK_WIDGET(g_datalist_get_data(widset, "file-treeview-widget")); selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(widget)); model = gtk_tree_view_get_model(GTK_TREE_VIEW(widget)); if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { mark: if (gtk_tree_selection_iter_is_selected(selection, &iter)) { if (gtk_list_store_remove(GTK_LIST_STORE(model), &iter)) goto mark; break; } } while (gtk_tree_model_iter_next(model, &iter)); } void ShareFile::SetPassword(GData **widset) { GtkWidget *widget, *parent; char *passwd, *epasswd; parent = GTK_WIDGET(g_datalist_get_data(widset, "dialog-widget")); if (!(passwd = pop_password_settings(parent))) return; widget = GTK_WIDGET(g_datalist_get_data(widset, "password-button-widget")); epasswd = g_base64_encode((guchar *)passwd, strlen(passwd)); g_object_set_data_full(G_OBJECT(widget), "password", epasswd, GDestroyNotify(g_free)); g_free(passwd); } void ShareFile::ClearPassword(GData **widset) { GtkWidget *widget; widget = GTK_WIDGET(g_datalist_get_data(widset, "password-button-widget")); g_object_set_data(G_OBJECT(widget), "password", NULL); } /** * 接收拖拽文件信息. * @param sfile 共享文件类 * @param context the drag context * @param x where the drop happened * @param y where the drop happened * @param data the received data * @param info the info that has been registered with the target in the * GtkTargetList * @param time the timestamp at which the data was received */ void ShareFile::DragDataReceived(ShareFile *sfile, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time) { GSList *list; if (!ValidateDragData(data, context, time)) { return; } list = selection_data_get_path(data); sfile->AttachSharedFiles(list); g_slist_foreach(list, GFunc(g_free), NULL); g_slist_free(list); gtk_drag_finish(context, TRUE, FALSE, time); } /** * 文件树(file-tree)排序比较函数. * @param model network-model * @param a A GtkTreeIter in model * @param b Another GtkTreeIter in model * @return 比较值 */ gint ShareFile::FileTreeCompareFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b) { gchar *afilepath, *bfilepath; uint32_t afileattr, bfileattr; gint result; gtk_tree_model_get(model, a, 1, &afilepath, 4, &afileattr, -1); gtk_tree_model_get(model, b, 1, &bfilepath, 4, &bfileattr, -1); if (GET_MODE(afileattr) == GET_MODE(bfileattr)) result = strcmp(afilepath, bfilepath); else if (GET_MODE(afileattr) == IPMSG_FILE_REGULAR) result = 1; else result = -1; g_free(afilepath); g_free(bfilepath); return result; } } // namespace iptuxiptux-0.7.4/src/iptux/ShareFile.h000066400000000000000000000026511323207530100166460ustar00rootroot00000000000000// // C++ Interface: ShareFile // // Description: // 添加或删除共享文件,即管理共享文件 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_SHAREFILE_H #define IPTUX_SHAREFILE_H #include "iptux/mess.h" namespace iptux { class ShareFile { public: ShareFile(); ~ShareFile(); static void ShareEntry(GtkWidget *parent); private: void InitSublayer(); void ClearSublayer(); GtkWidget *CreateMainDialog(GtkWidget *parent); GtkWidget *CreateAllArea(); GtkTreeModel *CreateFileModel(); void FillFileModel(GtkTreeModel *model); GtkWidget *CreateFileTree(GtkTreeModel *model); void ApplySharedData(); void AttachSharedFiles(GSList *list); GSList *PickSharedFile(uint32_t fileattr); GData *widset; GData *mdlset; //回调处理部分 private: static void AddRegular(ShareFile *sfile); static void AddFolder(ShareFile *sfile); static void DeleteFiles(GData **widset); static void SetPassword(GData **widset); static void ClearPassword(GData **widset); static void DragDataReceived(ShareFile *sfile, GdkDragContext *context, gint x, gint y, GtkSelectionData *data, guint info, guint time); static gint FileTreeCompareFunc(GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/SoundSystem.cpp000066400000000000000000000121361323207530100176330ustar00rootroot00000000000000// // C++ Implementation: SoundSystem // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "SoundSystem.h" #ifdef HAVE_GST #include "iptux/ProgramData.h" #include "iptux/output.h" #include "iptux/utils.h" namespace iptux { /** * 类构造函数. */ SoundSystem::SoundSystem() : eltset(NULL), persist(false) { g_datalist_init(&eltset); gettimeofday(×tamp, NULL); } /** * 类析构函数. */ SoundSystem::~SoundSystem() { GstElement *pipeline; if ((pipeline = GST_ELEMENT(g_datalist_get_data(&eltset, "pipeline-element")))) gst_element_set_state(pipeline, GST_STATE_NULL); g_datalist_clear(&eltset); } /** * 初始化声音系统. */ void SoundSystem::InitSublayer() { GstElement *pipeline; GstElement *filesrc, *decode, *volume, *convert, *sink; GstBus *bus; gst_init(NULL, NULL); pipeline = gst_pipeline_new("sound-system"); g_datalist_set_data_full(&eltset, "pipeline-element", pipeline, GDestroyNotify(gst_object_unref)); filesrc = gst_element_factory_make("filesrc", "source"); g_datalist_set_data(&eltset, "filesrc-element", filesrc); decode = gst_element_factory_make("decodebin", "decode"); g_datalist_set_data(&eltset, "decode-element", decode); volume = gst_element_factory_make("volume", "volume"); g_datalist_set_data(&eltset, "volume-element", volume); convert = gst_element_factory_make("audioconvert", "convert"); g_datalist_set_data(&eltset, "convert-element", convert); sink = gst_element_factory_make("autoaudiosink", "output"); g_datalist_set_data(&eltset, "output-element", sink); gst_bin_add_many(GST_BIN(pipeline), filesrc, decode, volume, convert, sink, NULL); gst_element_link_many(filesrc, decode, NULL); gst_element_link_many(volume, convert, sink, NULL); g_signal_connect_swapped(decode, "pad-added", G_CALLBACK(LinkElement), &eltset); bus = gst_pipeline_get_bus(GST_PIPELINE(pipeline)); gst_bus_add_signal_watch(GST_BUS(bus)); g_signal_connect_swapped(bus, "message::error", G_CALLBACK(ErrorMessageOccur), this); g_signal_connect_swapped(bus, "message::eos", G_CALLBACK(EosMessageOccur), this); gst_object_unref(bus); g_object_set(volume, "volume", progdt.volume, NULL); } /** * 调整音量. * @param value 音量值 */ void SoundSystem::AdjustVolume(double value) { GstElement *volume; volume = GST_ELEMENT(g_datalist_get_data(&eltset, "volume-element")); g_object_set(volume, "volume", value, NULL); } /** * 播放音频文件. * @param file 音频文件 * @note 如果时间间隔过短,系统将会忽略后一个请求. */ void SoundSystem::Playing(const char *file) { GstElement *pipeline, *filesrc; struct timeval time; gettimeofday(&time, NULL); if (!FLAG_ISSET(progdt.sndfgs, 0) || (difftimeval(time, timestamp) < 0.1)) return; if (persist) EosMessageOccur(this); persist = true; filesrc = GST_ELEMENT(g_datalist_get_data(&eltset, "filesrc-element")); g_object_set(filesrc, "location", file, NULL); pipeline = GST_ELEMENT(g_datalist_get_data(&eltset, "pipeline-element")); gst_element_set_state(pipeline, GST_STATE_PLAYING); timestamp = time; } /** * 停止播放. */ void SoundSystem::Stop() { EosMessageOccur(this); } /** * 链接元素. */ void SoundSystem::LinkElement(GData **eltset, GstPad *pad) { GstElement *volume; GstCaps *caps; GstStructure *str; GstPad *spad; caps = gst_pad_query_caps(pad, NULL); str = gst_caps_get_structure(caps, 0); volume = GST_ELEMENT(g_datalist_get_data(eltset, "volume-element")); if (strcasestr(gst_structure_get_name(str), "audio") && (spad = gst_element_get_compatible_pad(volume, pad, caps))) gst_pad_link(pad, spad); gst_caps_unref(caps); } /** * 错误响应处理函数. */ void SoundSystem::ErrorMessageOccur(SoundSystem *sndsys, GstMessage *message) { GstElement *pipeline; GError *error; gst_message_parse_error(message, &error, NULL); pwarning(_("Failed to play the prompt tone, %s\n"), error->message); g_error_free(error); EosMessageOccur(sndsys); pipeline = GST_ELEMENT(g_datalist_get_data(&sndsys->eltset, "pipeline-element")); gst_element_set_state(pipeline, GST_STATE_NULL); } /** * 播放文件结束响应处理函数. */ void SoundSystem::EosMessageOccur(SoundSystem *sndsys) { GstElement *pipeline, *decode, *volume; pipeline = GST_ELEMENT(g_datalist_get_data(&sndsys->eltset, "pipeline-element")); gst_element_set_state(pipeline, GST_STATE_READY); decode = GST_ELEMENT(g_datalist_get_data(&sndsys->eltset, "decode-element")); volume = GST_ELEMENT(g_datalist_get_data(&sndsys->eltset, "volume-element")); gst_element_unlink(decode, volume); sndsys->persist = false; } } // namespace iptux #else namespace iptux { SoundSystem::SoundSystem() {} SoundSystem::~SoundSystem() {} void SoundSystem::InitSublayer() {} void SoundSystem::AdjustVolume(double value) {} void SoundSystem::Playing(const char *file) {} void SoundSystem::Stop() {} } // namespace iptux #endif iptux-0.7.4/src/iptux/SoundSystem.h000066400000000000000000000016451323207530100173030ustar00rootroot00000000000000// // C++ Interface: SoundSystem // // Description: // 声音系统 // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_SOUNDSYSTEM_H #define IPTUX_SOUNDSYSTEM_H #include "iptux/config.h" #ifdef GST_FOUND #include #endif #include "iptux/mess.h" namespace iptux { class SoundSystem { public: SoundSystem(); ~SoundSystem(); void InitSublayer(); void AdjustVolume(double value); void Playing(const char *file); void Stop(); #ifdef GST_FOUND private: GData *eltset; //元素集 struct timeval timestamp; //时间戳 bool persist; //声音系统占用标记 private: static void LinkElement(GData **eltset, GstPad *pad); static void ErrorMessageOccur(SoundSystem *sndsys, GstMessage *message); static void EosMessageOccur(SoundSystem *sndsys); #endif }; } // namespace iptux #endif iptux-0.7.4/src/iptux/StatusIcon.cpp000066400000000000000000000176521323207530100174420ustar00rootroot00000000000000// // C++ Implementation: StatusIcon // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "StatusIcon.h" #include "DataSettings.h" #include "DetectPal.h" #include "DialogGroup.h" #include "DialogPeer.h" #include "ShareFile.h" #include "callback.h" #include "global.h" #include "iptux/deplib.h" #include "support.h" #include "utils.h" namespace iptux { /** * 类构造函数. */ StatusIcon::StatusIcon(IptuxConfig &config, MainWindow &mwin) : config(config), mwin(mwin), statusicon(NULL), timerid(0) {} /** * 类析构函数. */ StatusIcon::~StatusIcon() { if (statusicon) g_object_unref(statusicon); if (timerid > 0) g_source_remove(timerid); } /** * 创建状态图标. */ void StatusIcon::CreateStatusIcon() { GdkScreen *screen; if (g_progdt->IsAutoHidePanelAfterLogin()) { statusicon = gtk_status_icon_new_from_stock("iptux-logo-hide"); g_object_set_data(G_OBJECT(statusicon), "show", GINT_TO_POINTER(FALSE)); } else { statusicon = gtk_status_icon_new_from_stock("iptux-logo-show"); g_object_set_data(G_OBJECT(statusicon), "show", GINT_TO_POINTER(TRUE)); } screen = gdk_screen_get_default(); gtk_status_icon_set_screen(statusicon, screen); g_signal_connect_swapped(statusicon, "activate", G_CALLBACK(StatusIconActivate), this); g_signal_connect_swapped(statusicon, "popup-menu", G_CALLBACK(onPopupMenu), this); g_object_set(statusicon, "has-tooltip", TRUE, NULL); g_signal_connect(statusicon, "query-tooltip", G_CALLBACK(StatusIconQueryTooltip), NULL); } /** * 更改状态图标的表现形式. */ void StatusIcon::AlterStatusIconMode() { if (g_object_get_data(G_OBJECT(statusicon), "show")) { gtk_status_icon_set_from_stock(statusicon, "iptux-logo-hide"); g_object_set_data(G_OBJECT(statusicon), "show", GINT_TO_POINTER(FALSE)); } else { gtk_status_icon_set_from_stock(statusicon, "iptux-logo-show"); g_object_set_data(G_OBJECT(statusicon), "show", GINT_TO_POINTER(TRUE)); } } /** * 创建弹出菜单. * @return 菜单 */ GtkWidget *StatusIcon::CreatePopupMenu() { GtkWidget *menu, *menuitem; GtkWidget *image, *window; window = mwin.ObtainWindow(); menu = gtk_menu_new(); /* 显示&隐藏面板 */ if (g_object_get_data(G_OBJECT(statusicon), "show")) menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Hide")); else menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Show")); image = gtk_image_new_from_icon_name("menu-board", GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(onActivate), this); menuitem = gtk_separator_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); /* 显示文件传输窗口 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Transmission")); image = gtk_image_new_from_stock(GTK_STOCK_CONNECT, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ShowTransWindow), this); /* 首选项 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Preferences")); image = gtk_image_new_from_stock(GTK_STOCK_PREFERENCES, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(DataSettings::ResetDataEntry), window); /* 共享文件管理 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Shared Management")); image = gtk_image_new_from_icon_name("menu-share", GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(ShareFile::ShareEntry), window); menuitem = gtk_separator_menu_item_new(); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); /* 探测好友 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Detect")); image = gtk_image_new_from_icon_name("menu-detect", GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect_swapped(menuitem, "activate", G_CALLBACK(DetectPal::DetectEntry), window); /* 程序退出 */ NO_OPERATION_C menuitem = gtk_image_menu_item_new_with_mnemonic(_("_Quit")); image = gtk_image_new_from_stock(GTK_STOCK_QUIT, GTK_ICON_SIZE_MENU); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menuitem), image); gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); g_signal_connect(menuitem, "activate", G_CALLBACK(iptux_gui_quit), NULL); return menu; } /** * 显示文件传输窗口. */ void StatusIcon::ShowTransWindow(StatusIcon *self) { self->mwin.OpenTransWindow(); } /** * 状态图标被激活的响应处理函数. */ void StatusIcon::StatusIconActivate(StatusIcon *self) { GroupInfo *grpinf; g_cthrd->Lock(); if (g_cthrd->GetMsglineItems()) grpinf = g_cthrd->GetMsglineHeadItem(); else grpinf = NULL; g_cthrd->Unlock(); if (grpinf) { switch (grpinf->type) { case GROUP_BELONG_TYPE_REGULAR: DialogPeer::PeerDialogEntry(self->config, grpinf, self->getProgramData()); break; case GROUP_BELONG_TYPE_SEGMENT: case GROUP_BELONG_TYPE_GROUP: case GROUP_BELONG_TYPE_BROADCAST: DialogGroup::GroupDialogEntry(self->config, grpinf, self->getProgramData()); break; default: break; } } else { onActivate(self); } } /** * 弹出菜单. * @param statusicon the object which received the signal * @param button the button that was pressed * @param time the timestamp of the event that triggered the signal emission */ void StatusIcon::onPopupMenu(StatusIcon *self, guint button, guint time) { GtkWidget *menu; menu = self->CreatePopupMenu(); gtk_widget_show_all(menu); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, button, time); } /** * 状态图标信息提示查询请求. * @param statusicon the object which received the signal * @param x the x coordinate of the cursor position * @param y the y coordinate of the cursor position * @param key TRUE if the tooltip was trigged using the keyboard * @param tooltip a GtkTooltip * @return Gtk+库所需 */ gboolean StatusIcon::StatusIconQueryTooltip(GtkStatusIcon *statusicon, gint x, gint y, gboolean key, GtkTooltip *tooltip) { char *msgstr; guint len; /* 获取消息串 */ g_cthrd->Lock(); if ((len = g_cthrd->GetMsglineItems())) { msgstr = g_strdup_printf(_("To be read: %u messages"), len); } else { msgstr = get_sys_host_addr_string(g_cthrd->UdpSockQuote()); msgstr = msgstr ? msgstr : g_strdup(_("iptux")); } g_cthrd->Unlock(); /* 设置信息提示串 */ gtk_tooltip_set_text(tooltip, msgstr); g_free(msgstr); return TRUE; } /** * 状态图标是否嵌入到状态栏. * @return 是否已嵌入 */ gboolean StatusIcon::IsEmbedded() { embedded = gtk_status_icon_is_embedded(statusicon); return embedded; } /** * 改变UI的外观. * @return Gtk+库所需 */ gboolean StatusIcon::onActivate(StatusIcon *self) { return self->AlterInterfaceMode(); } gboolean StatusIcon::AlterInterfaceMode() { AlterStatusIconMode(); if (IsEmbedded()) { mwin.AlterWindowMode(); } else { gtk_main_quit(); } return TRUE; } } // namespace iptux iptux-0.7.4/src/iptux/StatusIcon.h000066400000000000000000000024411323207530100170750ustar00rootroot00000000000000// // C++ Interface: StatusIcon // // Description: // 创建状态栏图标 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_STATUSICON_H #define IPTUX_STATUSICON_H #include "iptux/IptuxConfig.h" #include "iptux/MainWindow.h" namespace iptux { class StatusIcon { public: StatusIcon(IptuxConfig& config, MainWindow& mwin); ~StatusIcon(); void CreateStatusIcon(); gboolean IsEmbedded(); void AlterStatusIconMode(); gboolean AlterInterfaceMode(); private: IptuxConfig& config; MainWindow& mwin; GtkStatusIcon* statusicon; guint timerid; gboolean embedded; private: ProgramData& getProgramData() { return mwin.GetProgramData(); } static gboolean UpdateUI(StatusIcon* sicon); GtkWidget* CreatePopupMenu(); //回调处理部分 private: static void ShowTransWindow(StatusIcon* self); static void StatusIconActivate(StatusIcon* self); static void onPopupMenu(StatusIcon* self, guint button, guint time); static gboolean StatusIconQueryTooltip(GtkStatusIcon* statusicon, gint x, gint y, gboolean key, GtkTooltip* tooltip); static gboolean onActivate(StatusIcon* self); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/TcpData.cpp000066400000000000000000000113421323207530100166540ustar00rootroot00000000000000// // C++ Implementation: TcpData // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "TcpData.h" #include #include #include "SendFile.h" #include "global.h" #include "iptux/deplib.h" #include "utils.h" #include "wrapper.h" namespace iptux { /** * 类构造函数. */ TcpData::TcpData() : sock(-1), size(0) {} /** * 类析构函数. */ TcpData::~TcpData() { close(sock); } /** * TCP连接处理入口. * @param sock tcp socket */ void TcpData::TcpDataEntry(int sock) { TcpData tdata; tdata.sock = sock; tdata.DispatchTcpData(); } /** * 分派TCP数据处理方案. */ void TcpData::DispatchTcpData() { uint32_t commandno; ssize_t len; /* 读取消息前缀 */ if ((len = read_ipmsg_prefix(sock, buf, MAX_SOCKLEN)) <= 0) return; /* 分派消息 */ size = len; //设置缓冲区数据的有效长度 commandno = iptux_get_dec_number(buf, ':', 4); //获取命令字 switch (GET_MODE(commandno)) { case IPMSG_GETFILEDATA: RequestData(IPMSG_FILE_REGULAR); break; case IPMSG_GETDIRFILES: RequestData(IPMSG_FILE_DIR); break; case IPTUX_SENDSUBLAYER: RecvSublayer(GET_OPT(commandno)); break; default: break; } } /** * 请求文件(目录)数据. * @param fileattr 文件类型 */ void TcpData::RequestData(uint32_t fileattr) { SendFile sfile; const char *attachptr; char *attach; attachptr = iptux_skip_section(buf, ':', 5); switch (GET_MODE(fileattr)) { case IPMSG_FILE_REGULAR: read_ipmsg_filedata(sock, (void *)attachptr, buf + MAX_SOCKLEN - attachptr, buf + size - attachptr); break; case IPMSG_FILE_DIR: read_ipmsg_dirfiles(sock, (void *)attachptr, buf + MAX_SOCKLEN - attachptr, buf + size - attachptr); break; default: break; } attach = ipmsg_get_attach(buf, ':', 5); sfile.RequestDataEntry(sock, fileattr, attach); g_free(attach); } /** * 接收底层数据. * @param cmdopt 命令字选项 */ void TcpData::RecvSublayer(uint32_t cmdopt) { static uint32_t count = 0; char path[MAX_PATHLEN]; struct sockaddr_in addr; socklen_t len; PalInfo *pal; int fd; /* 检查好友是否存在 */ len = sizeof(addr); getpeername(sock, (struct sockaddr *)&addr, &len); if (!(pal = g_cthrd->GetPalFromList(addr.sin_addr.s_addr))) return; /* 创建即将接收的数据文件路径 */ switch (GET_OPT(cmdopt)) { case IPTUX_PHOTOPICOPT: snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH "/%" PRIx32, g_get_user_cache_dir(), pal->ipv4); break; case IPTUX_MSGPICOPT: snprintf(path, MAX_PATHLEN, "%s" PIC_PATH "/%" PRIx32 "-%" PRIx32 "-%lx", g_get_user_cache_dir(), pal->ipv4, count++, time(NULL)); break; default: snprintf(path, MAX_PATHLEN, "%s" IPTUX_PATH "/%" PRIx32 "-%" PRIx32 "-%lx", g_get_user_cache_dir(), pal->ipv4, count++, time(NULL)); break; } /* 终于可以接收数据了^_^ */ if ((fd = open(path, O_WRONLY | O_CREAT | O_TRUNC, 0644)) == -1) return; RecvSublayerData(fd, strlen(buf) + 1); close(fd); /* 分派数据 */ switch (GET_OPT(cmdopt)) { case IPTUX_PHOTOPICOPT: RecvPhotoPic(pal, path); break; case IPTUX_MSGPICOPT: RecvMsgPic(pal, path); break; default: break; } } /** * 接收数据. * @param fd file descriptor * @param len 缓冲区无效数据长度 */ void TcpData::RecvSublayerData(int fd, size_t len) { ssize_t ssize; if (size != len) xwrite(fd, buf + len, size - len); do { if ((ssize = xread(sock, buf, MAX_SOCKLEN)) <= 0) break; if ((ssize = xwrite(fd, buf, ssize)) <= 0) break; } while (1); } /** * 接收好友形象照片. * @param pal class PalInfo * @param path file path */ void TcpData::RecvPhotoPic(PalInfo *pal, const char *path) { g_free(pal->photo); pal->photo = g_strdup(path); gdk_threads_enter(); g_cthrd->Lock(); g_cthrd->UpdatePalToList(pal->ipv4); g_cthrd->Unlock(); g_mwin->UpdateItemToPaltree(pal->ipv4); gdk_threads_leave(); } /** * 接收消息图片. * @param pal class PalInfo * @param path file path */ void TcpData::RecvMsgPic(PalInfo *pal, const char *path) { MsgPara para; ChipData *chip; /* 构建消息封装包 */ para.pal = pal; para.stype = MESSAGE_SOURCE_TYPE_PAL; para.btype = GROUP_BELONG_TYPE_REGULAR; chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_PICTURE; chip->data = g_strdup(path); para.dtlist = g_slist_append(NULL, chip); /* 交给某人处理吧 */ g_cthrd->InsertMessage(¶); } } // namespace iptuxiptux-0.7.4/src/iptux/TcpData.h000066400000000000000000000015171323207530100163240ustar00rootroot00000000000000// // C++ Interface: TcpData // // Description: // 对TCP连接进行处理 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_TCPDATA_H #define IPTUX_TCPDATA_H #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class TcpData { public: TcpData(); ~TcpData(); static void TcpDataEntry(int sock); private: void DispatchTcpData(); void RequestData(uint32_t fileattr); void RecvSublayer(uint32_t cmdopt); void RecvSublayerData(int fd, size_t len); void RecvPhotoPic(PalInfo *pal, const char *path); void RecvMsgPic(PalInfo *pal, const char *path); int sock; //数据交流套接口 size_t size; //缓冲区已使用长度 char buf[MAX_SOCKLEN]; //缓冲区 }; } // namespace iptux #endif iptux-0.7.4/src/iptux/TestMain.cpp000066400000000000000000000002021323207530100170510ustar00rootroot00000000000000#include "gtest/gtest.h" int main(int argc, char **argv) { ::testing::InitGoogleTest(&argc, argv); return RUN_ALL_TESTS(); } iptux-0.7.4/src/iptux/UdpData.cpp000066400000000000000000000542701323207530100166650ustar00rootroot00000000000000// // C++ Implementation: UdpData // // Description: // // // Author: cwll ,(C)2012 // Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // 2012.02 在接收消息中去掉了群组模式,群组模式只用来发消息 // #include "UdpData.h" #include #include #include "Command.h" #include "CoreThread.h" #include "DialogGroup.h" #include "DialogPeer.h" #include "MainWindow.h" #include "ProgramData.h" #include "RecvFile.h" #include "SendFile.h" #include "SoundSystem.h" #include "dialog.h" #include "global.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "utils.h" #include "wrapper.h" using namespace std; namespace iptux { /** * 类构造函数. */ UdpData::UdpData(IptuxConfig &config) : config(config), ipv4(0), size(0), encode(NULL) {} /** * 类析构函数. */ UdpData::~UdpData() { g_free(encode); } /** * UDP数据解析入口. * @param ipv4 ipv4 * @param buf[] 数据缓冲区 * @param size 数据有效长度 */ void UdpData::UdpDataEntry(IptuxConfig &config, in_addr_t ipv4, const char buf[], size_t size) { UdpData udata(config); udata.ipv4 = ipv4; udata.size = size < MAX_UDPLEN ? size : MAX_UDPLEN; memcpy(udata.buf, buf, size); if (size != MAX_UDPLEN) udata.buf[size] = '\0'; udata.DispatchUdpData(); } /** * 分派UDP数据到相应的函数去进行处理. */ void UdpData::DispatchUdpData() { uint32_t commandno; /* 如果开启了黑名单处理功能,且此地址正好被列入了黑名单 */ /* 嘿嘿,那就不要怪偶心狠手辣了 */ if (g_progdt->IsUsingBlacklist() && g_cthrd->BlacklistContainItem(ipv4)) return; /* 决定消息去向 */ commandno = iptux_get_dec_number(buf, ':', 4); switch (GET_MODE(commandno)) { case IPMSG_BR_ENTRY: SomeoneEntry(); break; case IPMSG_BR_EXIT: SomeoneExit(); break; case IPMSG_ANSENTRY: SomeoneAnsentry(); break; case IPMSG_BR_ABSENCE: SomeoneAbsence(); break; case IPMSG_SENDMSG: SomeoneSendmsg(); break; case IPMSG_RECVMSG: SomeoneRecvmsg(); break; case IPTUX_ASKSHARED: SomeoneAskShared(); break; case IPTUX_SENDICON: SomeoneSendIcon(); break; case IPTUX_SENDSIGN: SomeoneSendSign(); break; case IPTUX_SENDMSG: SomeoneBcstmsg(); break; default: break; } } /** * 好友信息数据丢失默认处理函数. * 若xx并不在好友列表中,但是程序却期望能够接受xx的本次会话, * 所以必须以默认数据构建好友信息数据并插入好友列表 \n */ void UdpData::SomeoneLost() { PalInfo *pal; /* 创建好友数据 */ pal = new PalInfo; pal->ipv4 = ipv4; pal->segdes = g_progdt->FindNetSegDescription(ipv4); if (!(pal->version = iptux_get_section_string(buf, ':', 0))) pal->version = g_strdup("?"); if (!(pal->user = iptux_get_section_string(buf, ':', 2))) pal->user = g_strdup("???"); if (!(pal->host = iptux_get_section_string(buf, ':', 3))) pal->host = g_strdup("???"); pal->name = g_strdup(_("mysterious")); pal->group = g_strdup(_("mysterious")); pal->photo = NULL; pal->sign = NULL; pal->iconfile = g_strdup(g_progdt->palicon); pal->encode = g_strdup(encode ? encode : "utf-8"); FLAG_SET(pal->flags, 1); pal->packetn = 0; pal->rpacketn = 0; /* 加入好友列表 */ gdk_threads_enter(); g_cthrd->Lock(); g_cthrd->AttachPalToList(pal); g_cthrd->Unlock(); g_mwin->AttachItemToPaltree(ipv4); gdk_threads_leave(); } /** * 好友上线. */ void UdpData::SomeoneEntry() { Command cmd; pthread_t pid; PalInfo *pal; /* 转换缓冲区数据编码 */ ConvertEncode(g_progdt->encode); /* 加入或更新好友列表 */ gdk_threads_enter(); g_cthrd->Lock(); if ((pal = g_cthrd->GetPalFromList(ipv4))) { UpdatePalInfo(pal); g_cthrd->UpdatePalToList(ipv4); } else { pal = CreatePalInfo(); g_cthrd->AttachPalToList(pal); } g_cthrd->Unlock(); if (g_mwin->PaltreeContainItem(ipv4)) g_mwin->UpdateItemToPaltree(ipv4); else g_mwin->AttachItemToPaltree(ipv4); gdk_threads_leave(); /* 通知好友本大爷在线 */ cmd.SendAnsentry(g_cthrd->UdpSockQuote(), pal); if (FLAG_ISSET(pal->flags, 0)) { pthread_create(&pid, NULL, ThreadFunc(CoreThread::SendFeatureData), pal); pthread_detach(pid); } } /** * 好友退出. */ void UdpData::SomeoneExit() { PalInfo *pal; /* 从好友链表中删除 */ gdk_threads_enter(); if (g_mwin->PaltreeContainItem(ipv4)) g_mwin->DelItemFromPaltree(ipv4); g_cthrd->Lock(); if ((pal = g_cthrd->GetPalFromList(ipv4))) { g_cthrd->DelPalFromList(ipv4); FLAG_CLR(pal->flags, 1); } g_cthrd->Unlock(); gdk_threads_leave(); } /** * 好友在线. */ void UdpData::SomeoneAnsentry() { Command cmd; pthread_t pid; PalInfo *pal; const char *ptr; /* 若好友不兼容iptux协议,则需转码 */ ptr = iptux_skip_string(buf, size, 3); if (!ptr || *ptr == '\0') ConvertEncode(g_progdt->encode); /* 加入或更新好友列表 */ gdk_threads_enter(); g_cthrd->Lock(); if ((pal = g_cthrd->GetPalFromList(ipv4))) { UpdatePalInfo(pal); g_cthrd->UpdatePalToList(ipv4); } else { pal = CreatePalInfo(); g_cthrd->AttachPalToList(pal); } g_cthrd->Unlock(); if (g_mwin->PaltreeContainItem(ipv4)) g_mwin->UpdateItemToPaltree(ipv4); else g_mwin->AttachItemToPaltree(ipv4); gdk_threads_leave(); /* 更新本大爷的数据信息 */ if (FLAG_ISSET(pal->flags, 0)) { pthread_create(&pid, NULL, ThreadFunc(CoreThread::SendFeatureData), pal); pthread_detach(pid); } else if (strcasecmp(g_progdt->encode.c_str(), pal->encode) != 0) cmd.SendAnsentry(g_cthrd->UdpSockQuote(), pal); } /** * 好友更改个人信息. */ void UdpData::SomeoneAbsence() { PalInfo *pal; const char *ptr; /* 若好友不兼容iptux协议,则需转码 */ pal = g_cthrd->GetPalFromList(ipv4); //利用好友链表只增不减的特性,无须加锁 ptr = iptux_skip_string(buf, size, 3); if (!ptr || *ptr == '\0') { if (pal) { string s(pal->encode); ConvertEncode(s); } else { ConvertEncode(g_progdt->encode); } } /* 加入或更新好友列表 */ gdk_threads_enter(); g_cthrd->Lock(); if (pal) { UpdatePalInfo(pal); g_cthrd->UpdatePalToList(ipv4); } else { pal = CreatePalInfo(); g_cthrd->AttachPalToList(pal); } g_cthrd->Unlock(); if (g_mwin->PaltreeContainItem(ipv4)) g_mwin->UpdateItemToPaltree(ipv4); else g_mwin->AttachItemToPaltree(ipv4); gdk_threads_leave(); } /** * 好友发送消息. * */ void UdpData::SomeoneSendmsg() { GroupInfo *grpinf; PalInfo *pal; Command cmd; uint32_t commandno, packetno; char *text; pthread_t pid; DialogPeer *dlgpr; GtkWidget *window; /* 如果对方兼容iptux协议,则无须再转换编码 */ pal = g_cthrd->GetPalFromList(ipv4); if (!pal || !FLAG_ISSET(pal->flags, 0)) { if (pal) { ConvertEncode(pal->encode); } else { ConvertEncode(g_progdt->encode); } } /* 确保好友在线,并对编码作出适当调整 */ pal = AssertPalOnline(); if (strcasecmp(pal->encode, encode ? encode : "utf-8") != 0) { g_free(pal->encode); pal->encode = g_strdup(encode ? encode : "utf-8"); } /* 回复好友并检查此消息是否过时 */ commandno = iptux_get_dec_number(buf, ':', 4); packetno = iptux_get_dec_number(buf, ':', 1); if (commandno & IPMSG_SENDCHECKOPT) cmd.SendReply(g_cthrd->UdpSockQuote(), pal, packetno); if (packetno <= pal->packetn) return; pal->packetn = packetno; /* 插入消息&在消息队列中注册 */ text = ipmsg_get_attach(buf, ':', 5); if (text && *text != '\0') { /*/* 插入消息 */ // if ((commandno & IPMSG_BROADCASTOPT) || (commandno & // IPMSG_MULTICASTOPT)) // InsertMessage(pal, GROUP_BELONG_TYPE_BROADCAST, // text); // else InsertMessage(pal, GROUP_BELONG_TYPE_REGULAR, text); } g_free(text); /*/* 注册消息 */ g_cthrd->Lock(); // if ((commandno & IPMSG_BROADCASTOPT) || (commandno & // IPMSG_MULTICASTOPT)) // grpinf = g_cthrd->GetPalBroadcastItem(pal); // else grpinf = g_cthrd->GetPalRegularItem(pal); if (!grpinf->dialog && !g_cthrd->MsglineContainItem(grpinf)) g_cthrd->PushItemToMsgline(grpinf); g_cthrd->Unlock(); /* 标记位处理 先处理底层数据,后面显示窗口*/ if (commandno & IPMSG_FILEATTACHOPT) { if ((commandno & IPTUX_SHAREDOPT) && (commandno & IPTUX_PASSWDOPT)) { pthread_create(&pid, NULL, ThreadFunc(ThreadAskSharedPasswd), pal); pthread_detach(pid); } else RecvPalFile(); } window = GTK_WIDGET(grpinf->dialog); //这里不知道为什么运行时一直会提示window不是object dlgpr = (DialogPeer *)(g_object_get_data(G_OBJECT(window), "dialog")); if (grpinf->dialog) dlgpr->ShowDialogPeer(dlgpr); /* 是否直接弹出聊天窗口 */ if (g_progdt->IsAutoOpenCharDialog()) { gdk_threads_enter(); if (!(grpinf->dialog)) { // switch (grpinf->type) { // case GROUP_BELONG_TYPE_REGULAR: DialogPeer::PeerDialogEntry(config, grpinf, *g_progdt); // break; // case GROUP_BELONG_TYPE_SEGMENT: // case GROUP_BELONG_TYPE_GROUP: // case GROUP_BELONG_TYPE_BROADCAST: // DialogGroup::GroupDialogEntry(grpinf); // default: // break; // } } else { gtk_window_present(GTK_WINDOW(grpinf->dialog)); } gdk_threads_leave(); } /* 播放提示音 */ if (FLAG_ISSET(g_progdt->sndfgs, 1)) g_sndsys->Playing(g_progdt->msgtip); } /** * 好友接收到消息. */ void UdpData::SomeoneRecvmsg() { uint32_t packetno; PalInfo *pal; if ((pal = g_cthrd->GetPalFromList(ipv4))) { packetno = iptux_get_dec_number(buf, ':', 5); if (packetno == pal->rpacketn) pal->rpacketn = 0; //标记此包编号已经被回复 } } /** * 好友请求本计算机的共享文件. */ void UdpData::SomeoneAskShared() { Command cmd; pthread_t pid; PalInfo *pal; const char *limit; char *passwd; if (!(pal = g_cthrd->GetPalFromList(ipv4))) return; limit = g_cthrd->GetAccessPublicLimit(); if (!limit || *limit == '\0') { pthread_create(&pid, NULL, ThreadFunc(ThreadAskSharedFile), pal); pthread_detach(pid); } else if (!(iptux_get_dec_number(buf, ':', 4) & IPTUX_PASSWDOPT)) { cmd.SendFileInfo(g_cthrd->UdpSockQuote(), pal, IPTUX_SHAREDOPT | IPTUX_PASSWDOPT, ""); } else if ((passwd = ipmsg_get_attach(buf, ':', 5))) { if (strcmp(passwd, limit) == 0) { pthread_create(&pid, NULL, ThreadFunc(ThreadAskSharedFile), pal); pthread_detach(pid); } g_free(passwd); } } /** * 好友发送头像数据. */ void UdpData::SomeoneSendIcon() { PalInfo *pal; char *iconfile; if (!(pal = g_cthrd->GetPalFromList(ipv4)) || FLAG_ISSET(pal->flags, 2)) return; /* 接收并更新数据 */ if ((iconfile = RecvPalIcon())) { g_free(pal->iconfile); pal->iconfile = iconfile; gdk_threads_enter(); g_cthrd->Lock(); g_cthrd->UpdatePalToList(ipv4); g_cthrd->Unlock(); g_mwin->UpdateItemToPaltree(ipv4); gdk_threads_leave(); } } /** * 好友发送个性签名. */ void UdpData::SomeoneSendSign() { PalInfo *pal; char *sign; if (!(pal = g_cthrd->GetPalFromList(ipv4))) return; /* 若好友不兼容iptux协议,则需转码 */ if (!FLAG_ISSET(pal->flags, 0)) ConvertEncode(pal->encode); /* 对编码作适当调整 */ if (strcasecmp(pal->encode, encode ? encode : "utf-8") != 0) { g_free(pal->encode); pal->encode = g_strdup(encode ? encode : "utf-8"); } /* 更新 */ if ((sign = ipmsg_get_attach(buf, ':', 5))) { g_free(pal->sign); pal->sign = sign; gdk_threads_enter(); g_cthrd->Lock(); g_cthrd->UpdatePalToList(ipv4); g_cthrd->Unlock(); g_mwin->UpdateItemToPaltree(ipv4); gdk_threads_leave(); } } /** * 好友广播消息. */ void UdpData::SomeoneBcstmsg() { GroupInfo *grpinf; PalInfo *pal; uint32_t commandno, packetno; char *text; /* 如果对方兼容iptux协议,则无须再转换编码 */ pal = g_cthrd->GetPalFromList(ipv4); if (!pal || !FLAG_ISSET(pal->flags, 0)) { if (pal) { ConvertEncode(pal->encode); } else { ConvertEncode(g_progdt->encode); } } /* 确保好友在线,并对编码作出适当调整 */ pal = AssertPalOnline(); if (strcasecmp(pal->encode, encode ? encode : "utf-8") != 0) { g_free(pal->encode); pal->encode = g_strdup(encode ? encode : "utf-8"); } /* 检查此消息是否过时 */ packetno = iptux_get_dec_number(buf, ':', 1); if (packetno <= pal->packetn) return; pal->packetn = packetno; /* 插入消息&在消息队列中注册 */ text = ipmsg_get_attach(buf, ':', 5); if (text && *text != '\0') { commandno = iptux_get_dec_number(buf, ':', 4); /*/* 插入消息 */ switch (GET_OPT(commandno)) { case IPTUX_BROADCASTOPT: InsertMessage(pal, GROUP_BELONG_TYPE_BROADCAST, text); break; case IPTUX_GROUPOPT: InsertMessage(pal, GROUP_BELONG_TYPE_GROUP, text); break; case IPTUX_SEGMENTOPT: InsertMessage(pal, GROUP_BELONG_TYPE_SEGMENT, text); break; case IPTUX_REGULAROPT: default: InsertMessage(pal, GROUP_BELONG_TYPE_REGULAR, text); break; } /*/* 注册消息 */ g_cthrd->Lock(); switch (GET_OPT(commandno)) { case IPTUX_BROADCASTOPT: grpinf = g_cthrd->GetPalBroadcastItem(pal); break; case IPTUX_GROUPOPT: grpinf = g_cthrd->GetPalGroupItem(pal); break; case IPTUX_SEGMENTOPT: grpinf = g_cthrd->GetPalSegmentItem(pal); break; case IPTUX_REGULAROPT: default: grpinf = g_cthrd->GetPalRegularItem(pal); break; } if (!grpinf->dialog && !g_cthrd->MsglineContainItem(grpinf)) g_cthrd->PushItemToMsgline(grpinf); g_cthrd->Unlock(); } g_free(text); /* 播放提示音 */ if (FLAG_ISSET(g_progdt->sndfgs, 1)) g_sndsys->Playing(g_progdt->msgtip); } /** * 创建好友信息数据. * @return 好友数据 */ PalInfo *UdpData::CreatePalInfo() { PalInfo *pal; pal = new PalInfo; pal->ipv4 = ipv4; pal->segdes = g_progdt->FindNetSegDescription(ipv4); if (!(pal->version = iptux_get_section_string(buf, ':', 0))) pal->version = g_strdup("?"); if (!(pal->user = iptux_get_section_string(buf, ':', 2))) pal->user = g_strdup("???"); if (!(pal->host = iptux_get_section_string(buf, ':', 3))) pal->host = g_strdup("???"); if (!(pal->name = ipmsg_get_attach(buf, ':', 5))) pal->name = g_strdup(_("mysterious")); pal->group = GetPalGroup(); pal->photo = NULL; pal->sign = NULL; if (!(pal->iconfile = GetPalIcon())) pal->iconfile = g_strdup(g_progdt->palicon); if ((pal->encode = GetPalEncode())) FLAG_SET(pal->flags, 0); else pal->encode = g_strdup(encode ? encode : "utf-8"); FLAG_SET(pal->flags, 1); pal->packetn = 0; pal->rpacketn = 0; return pal; } /** * 更新好友信息数据. * @param pal 好友数据 */ void UdpData::UpdatePalInfo(PalInfo *pal) { g_free(pal->segdes); pal->segdes = g_progdt->FindNetSegDescription(ipv4); g_free(pal->version); if (!(pal->version = iptux_get_section_string(buf, ':', 0))) pal->version = g_strdup("?"); g_free(pal->user); if (!(pal->user = iptux_get_section_string(buf, ':', 2))) pal->user = g_strdup("???"); g_free(pal->host); if (!(pal->host = iptux_get_section_string(buf, ':', 3))) pal->host = g_strdup("???"); if (!FLAG_ISSET(pal->flags, 2)) { g_free(pal->name); if (!(pal->name = ipmsg_get_attach(buf, ':', 5))) pal->name = g_strdup(_("mysterious")); g_free(pal->group); pal->group = GetPalGroup(); g_free(pal->iconfile); if (!(pal->iconfile = GetPalIcon())) pal->iconfile = g_strdup(g_progdt->palicon); FLAG_CLR(pal->flags, 0); g_free(pal->encode); if ((pal->encode = GetPalEncode())) FLAG_SET(pal->flags, 0); else pal->encode = g_strdup(encode ? encode : "utf-8"); } FLAG_SET(pal->flags, 1); pal->packetn = 0; pal->rpacketn = 0; } /** * 插入消息. * @param pal class PalInfo * @param btype 消息所属类型 * @param msg 消息 */ void UdpData::InsertMessage(PalInfo *pal, GroupBelongType btype, const char *msg) { MsgPara para; ChipData *chip; /* 构建消息封装包 */ para.pal = pal; para.stype = MESSAGE_SOURCE_TYPE_PAL; para.btype = btype; chip = new ChipData; chip->type = MESSAGE_CONTENT_TYPE_STRING; chip->data = g_strdup(msg); para.dtlist = g_slist_append(NULL, chip); /* 交给某人处理吧 */ g_cthrd->InsertMessage(¶); } void UdpData::ConvertEncode(const char *enc) { string encode(enc); ConvertEncode(encode); } /** * 将缓冲区中的数据转换为utf8编码. * @param enc 原数据首选编码 */ void UdpData::ConvertEncode(const string &enc) { char *ptr; size_t len; /* 将缓冲区内有效的'\0'字符转换为ASCII字符 */ ptr = buf + strlen(buf) + 1; while ((size_t)(ptr - buf) <= size) { *(ptr - 1) = NULL_OBJECT; ptr += strlen(ptr) + 1; } /* 转换字符集编码 */ /** * @note 请不要采用以下做法,它在某些环境下将导致致命错误: \n * if (g_utf8_validate(buf, -1, NULL)) {encode = g_strdup("utf-8")} \n * e.g. 系统编码为GB18030的xx发送来纯ASCII字符串 \n */ if (!enc.empty() && strcasecmp(enc.c_str(), "utf-8") != 0 && (ptr = convert_encode(buf, "utf-8", enc.c_str()))) encode = g_strdup(enc.c_str()); else ptr = iptux_string_validate(buf, g_progdt->codeset, &encode); if (ptr) { len = strlen(ptr); size = len < MAX_UDPLEN ? len : MAX_UDPLEN; memcpy(buf, ptr, size); if (size < MAX_UDPLEN) buf[size] = '\0'; g_free(ptr); } /* 将缓冲区内的ASCII字符还原为'\0'字符 */ ptr = buf; while ((ptr = (char *)memchr(ptr, NULL_OBJECT, buf + size - ptr))) { *ptr = '\0'; ptr++; } } /** * 获取好友群组名称. * @return 群组 */ char *UdpData::GetPalGroup() { const char *ptr; if ((ptr = iptux_skip_string(buf, size, 1)) && *ptr != '\0') return g_strdup(ptr); return NULL; } /** * 获取好友头像图标. * @return 头像 */ char *UdpData::GetPalIcon() { char path[MAX_PATHLEN]; const char *ptr; if ((ptr = iptux_skip_string(buf, size, 2)) && *ptr != '\0') { snprintf(path, MAX_PATHLEN, __PIXMAPS_PATH "/icon/%s", ptr); if (access(path, F_OK) == 0) return g_strdup(ptr); } return NULL; } /** * 获取好友系统编码. * @return 编码 */ char *UdpData::GetPalEncode() { const char *ptr; if ((ptr = iptux_skip_string(buf, size, 3)) && *ptr != '\0') return g_strdup(ptr); return NULL; } /** * 接收好友头像数据. * @return 头像文件名 */ char *UdpData::RecvPalIcon() { GdkPixbuf *pixbuf; char path[MAX_PATHLEN]; char *iconfile; size_t len; int fd; /* 若无头像数据则返回null */ if ((len = strlen(buf) + 1) >= size) return NULL; /* 将头像数据刷入磁盘 */ snprintf(path, MAX_PATHLEN, "%s" ICON_PATH "/%" PRIx32, g_get_user_cache_dir(), ipv4); if ((fd = open(path, O_WRONLY | O_CREAT | O_TRUNC, 0644)) == -1) return NULL; xwrite(fd, buf + len, size - len); close(fd); /* 将头像pixbuf加入内建 */ iconfile = NULL; gdk_threads_enter(); if ((pixbuf = gdk_pixbuf_new_from_file(path, NULL))) { iconfile = g_strdup_printf("%" PRIx32, ipv4); gtk_icon_theme_add_builtin_icon(iconfile, MAX_ICONSIZE, pixbuf); g_object_unref(pixbuf); } gdk_threads_leave(); return iconfile; } /** * 确保好友一定在线. * @return 好友数据 */ PalInfo *UdpData::AssertPalOnline() { PalInfo *pal; if ((pal = g_cthrd->GetPalFromList(ipv4))) { /* 既然好友不在线,那么他自然不在列表中 */ if (!FLAG_ISSET(pal->flags, 1)) { FLAG_SET(pal->flags, 1); gdk_threads_enter(); g_cthrd->Lock(); g_cthrd->UpdatePalToList(ipv4); g_cthrd->Unlock(); g_mwin->AttachItemToPaltree(ipv4); gdk_threads_leave(); } } else { SomeoneLost(); pal = g_cthrd->GetPalFromList(ipv4); } return pal; } /** * 接收好友文件信息. */ void UdpData::RecvPalFile() { uint32_t packetno, commandno; const char *ptr; pthread_t pid; GData *para; packetno = iptux_get_dec_number(buf, ':', 1); commandno = iptux_get_dec_number(buf, ':', 4); ptr = iptux_skip_string(buf, size, 1); /* 只有当此为共享文件信息或文件信息不为空才需要接收 */ if ((commandno & IPTUX_SHAREDOPT) || (ptr && *ptr != '\0')) { para = NULL; g_datalist_init(¶); g_datalist_set_data(¶, "palinfo", g_cthrd->GetPalFromList(ipv4)); g_datalist_set_data_full(¶, "extra-data", g_strdup(ptr), GDestroyNotify(g_free)); g_datalist_set_data(¶, "packetno", GUINT_TO_POINTER(packetno)); g_datalist_set_data(¶, "commandno", GUINT_TO_POINTER(commandno)); pthread_create(&pid, NULL, ThreadFunc(RecvFile::RecvEntry), para); pthread_detach(pid); } } /** * 请求获取好友共享文件的密码. * @param pal class PalInfo */ void UdpData::ThreadAskSharedPasswd(PalInfo *pal) { Command cmd; gchar *passwd, *epasswd; gdk_threads_enter(); passwd = pop_obtain_shared_passwd(pal); gdk_threads_leave(); if (passwd && *passwd != '\0') { epasswd = g_base64_encode((guchar *)passwd, strlen(passwd)); cmd.SendAskShared(g_cthrd->UdpSockQuote(), pal, IPTUX_PASSWDOPT, epasswd); g_free(epasswd); } g_free(passwd); } /** * 某好友请求本计算机的共享文件. * @param pal class PalInfo */ void UdpData::ThreadAskSharedFile(PalInfo *pal) { SendFile sfile; bool permit; if (g_progdt->IsFilterFileShareRequest()) { gdk_threads_enter(); permit = pop_request_shared_file(pal); gdk_threads_leave(); if (permit) sfile.SendSharedInfoEntry(pal); } else sfile.SendSharedInfoEntry(pal); } } // namespace iptux iptux-0.7.4/src/iptux/UdpData.h000066400000000000000000000031251323207530100163230ustar00rootroot00000000000000// // C++ Interface: UdpData // // Description: // 处理接收到的UDP数据 // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_UDPDATA_H #define IPTUX_UDPDATA_H #include #include "iptux/IptuxConfig.h" #include "iptux/ipmsg.h" #include "iptux/mess.h" namespace iptux { class UdpData { public: explicit UdpData(IptuxConfig &config); ~UdpData(); static void UdpDataEntry(IptuxConfig &config, in_addr_t ipv4, const char buf[], size_t size); private: void DispatchUdpData(); void SomeoneLost(); void SomeoneEntry(); void SomeoneExit(); void SomeoneAnsentry(); void SomeoneAbsence(); void SomeoneSendmsg(); void SomeoneRecvmsg(); void SomeoneAskShared(); void SomeoneSendIcon(); void SomeoneSendSign(); void SomeoneBcstmsg(); PalInfo *CreatePalInfo(); void UpdatePalInfo(PalInfo *pal); void InsertMessage(PalInfo *pal, GroupBelongType btype, const char *msg); void ConvertEncode(const std::string &enc); void ConvertEncode(const char *enc); char *GetPalGroup(); char *GetPalIcon(); char *GetPalEncode(); char *RecvPalIcon(); PalInfo *AssertPalOnline(); void RecvPalFile(); IptuxConfig &config; in_addr_t ipv4; //数据来自 size_t size; //缓冲区数据有效长度 char buf[MAX_UDPLEN]; //数据缓冲区 char *encode; //原数据编码(NULL意味着utf8) private: static void ThreadAskSharedPasswd(PalInfo *pal); static void ThreadAskSharedFile(PalInfo *pal); }; } // namespace iptux #endif iptux-0.7.4/src/iptux/UtilsTest.cpp000066400000000000000000000003301323207530100172670ustar00rootroot00000000000000#include "gtest/gtest.h" #include "iptux/utils.h" using namespace iptux; TEST(Utils, FLAG_SET) { uint8_t a = 1; FLAG_SET(a, 0, false); EXPECT_EQ(a, 0); a = 1; FLAG_SET(a, 1, true); EXPECT_EQ(a, 3); } iptux-0.7.4/src/iptux/WindowConfig.cpp000066400000000000000000000007531323207530100177350ustar00rootroot00000000000000#include "WindowConfig.h" namespace iptux { void WindowConfig::LoadFromConfig(IptuxConfig& config) { int width = config.GetInt(prefix + "_width"); if (width != 0) { this->width = width; } int height = config.GetInt(prefix + "_height"); if (height != 0) { this->height = height; } } void WindowConfig::SaveToConfig(IptuxConfig& config) { config.SetInt(prefix + "_width", width); config.SetInt(prefix + "_height", height); config.Save(); } } // namespace iptux iptux-0.7.4/src/iptux/WindowConfig.h000066400000000000000000000014441323207530100174000ustar00rootroot00000000000000#ifndef IPTUX_WINDOW_CONFIG_H #define IPTUX_WINDOW_CONFIG_H #include #include "iptux/IptuxConfig.h" namespace iptux { class WindowConfig { public: WindowConfig(int defaultWidth, int defaultHeight, std::string prefix) { this->width = defaultWidth; this->height = defaultHeight; this->prefix = prefix; } virtual ~WindowConfig() {} int GetWidth() const { return width; } WindowConfig& SetWidth(int width) { this->width = width; return *this; } int GetHeight() const { return height; } WindowConfig& SetHeight(int height) { this->height = height; return *this; } void LoadFromConfig(IptuxConfig& config); void SaveToConfig(IptuxConfig& config); private: int width; int height; std::string prefix; }; } // namespace iptux #endifiptux-0.7.4/src/iptux/callback.cpp000066400000000000000000000226371323207530100171010ustar00rootroot00000000000000// // C++ Implementation: callback // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "callback.h" #include #include #include "iptux/MainWindow.h" #include "iptux/ProgramData.h" #include "iptux/StatusIcon.h" #include "iptux/global.h" #include "iptux/ipmsg.h" #include "iptux/support.h" namespace iptux { /** * 给entry控件设置提示信息. * @param entry entry * @param x the x coordinate of the cursor position * @param y the y coordinate of the cursor position * @param key TRUE if the tooltip was trigged using the keyboard * @param tooltip a GtkTooltip * @param text text string * @return Gtk+库所需 */ gboolean entry_query_tooltip(GtkWidget *entry, gint x, gint y, gboolean key, GtkTooltip *tooltip, char *text) { GtkWidget *label; label = gtk_label_new(text); gtk_label_set_line_wrap(GTK_LABEL(label), TRUE); gtk_label_set_line_wrap_mode(GTK_LABEL(label), PANGO_WRAP_WORD_CHAR); gtk_tooltip_set_custom(tooltip, label); return TRUE; } /** * 保证entry控件只接收数字字符. * @param entry entry * @param text the new text to insert * @param length the length of the new text, in bytes, or -1 if new_text is * nul-terminated */ void entry_insert_numeric(GtkWidget *entry, gchar *text, gint length) { gint count; if (length == -1) length = strlen(text); count = 0; while (count < length) { if (!isdigit(*(text + count)) && !(*(text + count) == '.')) { g_signal_stop_emission_by_name(entry, "insert-text"); return; } count++; } } /** * 以可预览的方式选择文件. * @param title file chooser dialog title * @param parent parent * @return 文件名 */ gchar *choose_file_with_preview(const gchar *title, GtkWidget *parent) { GtkWidget *chooser, *preview; gchar *filename; chooser = gtk_file_chooser_dialog_new( title, GTK_WINDOW(parent), GTK_FILE_CHOOSER_ACTION_OPEN, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(chooser), GTK_RESPONSE_ACCEPT); gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(chooser), TRUE); gtk_file_chooser_set_select_multiple(GTK_FILE_CHOOSER(chooser), FALSE); gtk_file_chooser_set_do_overwrite_confirmation(GTK_FILE_CHOOSER(chooser), TRUE); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(chooser), g_get_home_dir()); preview = gtk_image_new(); gtk_widget_set_size_request(preview, MAX_PREVIEWSIZE, MAX_PREVIEWSIZE); gtk_file_chooser_set_preview_widget(GTK_FILE_CHOOSER(chooser), preview); gtk_file_chooser_set_preview_widget_active(GTK_FILE_CHOOSER(chooser), FALSE); g_signal_connect(chooser, "update-preview", G_CALLBACK(chooser_update_preview), preview); gtk_widget_show_all(chooser); filename = NULL; switch (gtk_dialog_run(GTK_DIALOG(chooser))) { case GTK_RESPONSE_ACCEPT: filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(chooser)); break; default: break; } gtk_widget_destroy(chooser); return filename; } /** * 更新文件选择器的预览控件. * @param chooser a file chooser * @param preview preview widget */ void chooser_update_preview(GtkFileChooser *chooser, GtkWidget *preview) { gchar *filename; GdkPixbuf *pixbuf; if (!(filename = gtk_file_chooser_get_preview_filename(chooser))) { gtk_file_chooser_set_preview_widget_active(chooser, FALSE); return; } pixbuf = gdk_pixbuf_new_from_file(filename, NULL); g_free(filename); if (!pixbuf) { gtk_file_chooser_set_preview_widget_active(chooser, FALSE); return; } pixbuf_shrink_scale_1(&pixbuf, MAX_PREVIEWSIZE, MAX_PREVIEWSIZE); gtk_image_set_from_pixbuf(GTK_IMAGE(preview), pixbuf); g_object_unref(pixbuf); gtk_file_chooser_set_preview_widget_active(chooser, TRUE); } void model_select_all(GtkTreeModel *model) { GtkTreeIter iter; if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { if (gtk_tree_model_get_flags(model) & GTK_TREE_MODEL_LIST_ONLY) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, TRUE, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), &iter, 0, TRUE, -1); } while (gtk_tree_model_iter_next(model, &iter)); } void model_turn_all(GtkTreeModel *model) { GtkTreeIter iter; gboolean active; if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { gtk_tree_model_get(model, &iter, 0, &active, -1); if (gtk_tree_model_get_flags(model) & GTK_TREE_MODEL_LIST_ONLY) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, !active, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), &iter, 0, !active, -1); } while (gtk_tree_model_iter_next(model, &iter)); } void model_clear_all(GtkTreeModel *model) { GtkTreeIter iter; if (!gtk_tree_model_get_iter_first(model, &iter)) return; do { if (gtk_tree_model_get_flags(model) & GTK_TREE_MODEL_LIST_ONLY) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, FALSE, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), &iter, 0, FALSE, -1); } while (gtk_tree_model_iter_next(model, &iter)); } void model_turn_select(GtkTreeModel *model, gchar *path) { GtkTreeIter iter; gboolean active; if (!gtk_tree_model_get_iter_from_string(model, &iter, path)) return; gtk_tree_model_get(model, &iter, 0, &active, -1); if (gtk_tree_model_get_flags(model) & GTK_TREE_MODEL_LIST_ONLY) gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, !active, -1); else gtk_tree_store_set(GTK_TREE_STORE(model), &iter, 0, !active, -1); } void textview_follow_if_link(GtkWidget *textview, GtkTextIter *iter) { GSList *tags, *tmp; GtkTextTag *tag; gchar *url; tmp = tags = gtk_text_iter_get_tags(iter); while (tmp) { tag = (GtkTextTag *)tmp->data; if ((url = (gchar *)g_object_get_data(G_OBJECT(tag), "url"))) { if (!gtk_show_uri(NULL, url, GDK_CURRENT_TIME, NULL)) { iptux_open_url(url); } break; } tmp = tmp->next; } g_slist_free(tags); } void textview_set_cursor_if_appropriate(GtkTextView *textview, gint x, gint y, ProgramData &progdt) { GdkWindow *window; GSList *tags, *tmp; GtkTextTag *tag; GtkTextIter iter; gboolean hovering; hovering = FALSE; gtk_text_view_get_iter_at_location(textview, &iter, x, y); tmp = tags = gtk_text_iter_get_tags(&iter); while (tmp) { tag = (GtkTextTag *)tmp->data; if (g_object_get_data(G_OBJECT(tag), "url")) { hovering = TRUE; break; } tmp = tmp->next; } g_slist_free(tags); if (hovering != GPOINTER_TO_INT(g_object_get_data(G_OBJECT(textview), "hovering-over-link"))) { window = gtk_text_view_get_window(textview, GTK_TEXT_WINDOW_TEXT); if (hovering) gdk_window_set_cursor(window, progdt.lcursor); else gdk_window_set_cursor(window, progdt.xcursor); g_object_set_data(G_OBJECT(textview), "hovering-over-link", GINT_TO_POINTER(hovering)); } } gboolean textview_key_press_event(GtkWidget *textview, GdkEventKey *event) { GtkTextBuffer *buffer; GtkTextIter iter; gint position; switch (event->keyval) { case GDK_KEY_Return: case GDK_KEY_KP_Enter: buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(textview)); g_object_get(buffer, "cursor-position", &position, NULL); gtk_text_buffer_get_iter_at_offset(buffer, &iter, position); textview_follow_if_link(textview, &iter); break; default: break; } return FALSE; } void textview_event_after(GtkWidget *textview, GdkEvent *ev) { GtkTextBuffer *buffer; GdkEventButton *event; GtkTextIter iter; gboolean selected; gint x, y; if (ev->type != GDK_BUTTON_RELEASE) return; event = (GdkEventButton *)ev; if (event->button != 1) return; /* we shouldn't follow a link if the user has selected something */ buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(textview)); g_object_get(buffer, "has-selection", &selected, NULL); if (selected) return; gtk_text_view_window_to_buffer_coords(GTK_TEXT_VIEW(textview), GTK_TEXT_WINDOW_WIDGET, event->x, event->y, &x, &y); gtk_text_view_get_iter_at_location(GTK_TEXT_VIEW(textview), &iter, x, y); textview_follow_if_link(textview, &iter); } gboolean textview_motion_notify_event(GtkWidget *textview, GdkEventMotion *event) { gint x, y; gtk_text_view_window_to_buffer_coords(GTK_TEXT_VIEW(textview), GTK_TEXT_WINDOW_WIDGET, event->x, event->y, &x, &y); textview_set_cursor_if_appropriate(GTK_TEXT_VIEW(textview), x, y, *g_progdt); gdk_window_get_pointer(gtk_widget_get_window(textview), NULL, NULL, NULL); return FALSE; } gboolean textview_visibility_notify_event(GtkWidget *textview, GdkEventVisibility *event) { gint wx, wy, bx, by; gdk_window_get_pointer(gtk_widget_get_window(textview), &wx, &wy, NULL); gtk_text_view_window_to_buffer_coords( GTK_TEXT_VIEW(textview), GTK_TEXT_WINDOW_WIDGET, wx, wy, &bx, &by); textview_set_cursor_if_appropriate(GTK_TEXT_VIEW(textview), bx, by, *g_progdt); return FALSE; } } // namespace iptux iptux-0.7.4/src/iptux/callback.h000066400000000000000000000027451323207530100165440ustar00rootroot00000000000000// // C++ Interface: callback // // Description: // 共用构建界面函数及回调函数集合 // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_CALLBACK_H #define IPTUX_CALLBACK_H #include "mess.h" namespace iptux { /* entry */ gboolean entry_query_tooltip(GtkWidget *entry, gint x, gint y, gboolean key, GtkTooltip *tooltip, char *text); void entry_insert_numeric(GtkWidget *entry, gchar *text, gint length); /* file-chooser */ gchar *choose_file_with_preview(const gchar *title, GtkWidget *parent); void chooser_update_preview(GtkFileChooser *chooser, GtkWidget *preview); /* model:0 G_TYPE_BOOLEAN */ void model_select_all(GtkTreeModel *model); void model_turn_all(GtkTreeModel *model); void model_clear_all(GtkTreeModel *model); void model_turn_select(GtkTreeModel *model, gchar *path); /* text view link */ void textview_follow_if_link(GtkWidget *textview, GtkTextIter *iter); void textview_set_cursor_if_appropriate(GtkTextView *textview, gint x, gint y); gboolean textview_key_press_event(GtkWidget *textview, GdkEventKey *event); void textview_event_after(GtkWidget *textview, GdkEvent *ev); gboolean textview_motion_notify_event(GtkWidget *textview, GdkEventMotion *event); gboolean textview_visibility_notify_event(GtkWidget *textview, GdkEventVisibility *event); } // namespace iptux #endif iptux-0.7.4/src/iptux/config.h.in000066400000000000000000000006071323207530100166550ustar00rootroot00000000000000#define VERSION "@PROJECT_VERSION@" #define IPTUX_VERSION "iptux @PROJECT_VERSION@" #define GETTEXT_PACKAGE "@PROJECT_NAME@" #define __PIXMAPS_PATH "@CMAKE_INSTALL_FULL_DATADIR@/iptux/pixmaps" #define __LOCALE_PATH "@CMAKE_INSTALL_FULL_DATADIR@/locale" #define __SOUND_PATH "@CMAKE_INSTALL_FULL_DATADIR@/iptux/sound" #cmakedefine GST_FOUND #ifdef __APPLE__ # define O_LARGEFILE 0 #endif iptux-0.7.4/src/iptux/deplib.h000066400000000000000000000011371323207530100162410ustar00rootroot00000000000000// // C++ Interface: deplib // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DEPLIB_H #define IPTUX_DEPLIB_H #undef _ #include #define ATOM_OBJECT 0xFFFC #define OCCUPY_OBJECT 0x01 #define NULL_OBJECT 0x02 #define GINT(x) ((gint)(x)) #define GCONF_PATH "/apps/iptux" #define IPTUX_PATH "/iptux" #define LOG_PATH "/iptux/log" #define PIC_PATH "/iptux/pic" #define ICON_PATH "/iptux/icon" #define PHOTO_PATH "/iptux/photo" #ifndef _ #define _(string) gettext(string) #endif #endif iptux-0.7.4/src/iptux/dialog.cpp000066400000000000000000000176501323207530100166030ustar00rootroot00000000000000// // C++ Implementation: dialog // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "dialog.h" #include "iptux/callback.h" #include "iptux/deplib.h" #include "iptux/global.h" #include "iptux/output.h" namespace iptux { /** * 弹出请求程序退出的对话框. * @return true|false */ bool pop_request_quit() { GtkWidget *dialog; gint result; dialog = gtk_message_dialog_new(GTK_WINDOW(g_mwin->ObtainWindow()), GTK_DIALOG_MODAL, GTK_MESSAGE_QUESTION, GTK_BUTTONS_OK_CANCEL, "%s", _("File transfer has not been completed.\n" "Are you sure to cancel and quit?")); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_CANCEL); gtk_window_set_title(GTK_WINDOW(dialog), _("Confirm Exit")); result = gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); return (result == GTK_RESPONSE_OK); } /** * 弹出好友请求获取本机共享文件的对话框. * @param pal class PalInfo * @return true|false */ bool pop_request_shared_file(PalInfo *pal) { GtkWidget *dialog, *box; GtkWidget *label, *image; char ipstr[INET_ADDRSTRLEN], *ptr; gint result; dialog = gtk_dialog_new_with_buttons( _("Request Shared Resources"), GTK_WINDOW(g_mwin->ObtainWindow()), GTK_DIALOG_MODAL, _("Agree"), GTK_RESPONSE_ACCEPT, _("Refuse"), GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); box = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), box, TRUE, TRUE, 0); image = gtk_image_new_from_stock(GTK_STOCK_DIALOG_QUESTION, GTK_ICON_SIZE_DIALOG); gtk_box_pack_start(GTK_BOX(box), image, FALSE, FALSE, 0); image = gtk_vseparator_new(); gtk_box_pack_start(GTK_BOX(box), image, FALSE, FALSE, 0); inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); ptr = g_strdup_printf(_("Your pal (%s)[%s]\n" "is requesting to get your shared resources,\n" "Do you agree?"), pal->name, ipstr); label = gtk_label_new(ptr); g_free(ptr); gtk_label_set_line_wrap(GTK_LABEL(label), TRUE); gtk_label_set_line_wrap_mode(GTK_LABEL(label), PANGO_WRAP_WORD_CHAR); gtk_box_pack_start(GTK_BOX(box), label, TRUE, TRUE, 4); gtk_widget_show_all(dialog); result = gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); return (result == GTK_RESPONSE_ACCEPT); } /** * 弹出请求获取好友共享文件的密码. * @param pal class PalInfo * @return password string */ char *pop_obtain_shared_passwd(PalInfo *pal) { GtkWidget *dialog, *frame, *box; GtkWidget *image, *passwd; char ipstr[INET_ADDRSTRLEN], *text; gint result; dialog = gtk_dialog_new_with_buttons( _("Access Password"), GTK_WINDOW(g_mwin->ObtainWindow()), GTK_DIALOG_MODAL, GTK_STOCK_OK, GTK_RESPONSE_OK, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); frame = gtk_frame_new(_("Please input the password for " "the shared files behind")); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), frame, FALSE, FALSE, 0); box = gtk_hbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(frame), box); image = gtk_image_new_from_stock(GTK_STOCK_DIALOG_AUTHENTICATION, GTK_ICON_SIZE_DIALOG); gtk_box_pack_start(GTK_BOX(box), image, FALSE, FALSE, 0); image = gtk_vseparator_new(); gtk_box_pack_start(GTK_BOX(box), image, FALSE, FALSE, 0); inet_ntop(AF_INET, &pal->ipv4, ipstr, INET_ADDRSTRLEN); text = g_strdup_printf(_("(%s)[%s]Password:"), pal->name, ipstr); frame = gtk_frame_new(text); gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_NONE); gtk_box_pack_start(GTK_BOX(box), frame, TRUE, TRUE, 0); g_free(text); passwd = gtk_entry_new(); gtk_entry_set_activates_default(GTK_ENTRY(passwd), TRUE); gtk_entry_set_visibility(GTK_ENTRY(passwd), FALSE); gtk_container_add(GTK_CONTAINER(frame), passwd); gtk_widget_show_all(dialog); text = NULL; //并无多大用处,主要用来避免编译警告 mark: switch (result = gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_OK: if (*(text = gtk_editable_get_chars(GTK_EDITABLE(passwd), 0, -1)) == '\0') { gtk_widget_grab_focus(passwd); pop_warning(dialog, _("\nEmpty Password!")); g_free(text); goto mark; } default: break; } gtk_widget_destroy(dialog); return (result == GTK_RESPONSE_OK ? text : NULL); } /** * 弹出密码设定的对话框. * @param parent parent window * @return password string */ char *pop_password_settings(GtkWidget *parent) { GtkWidget *dialog, *hbox, *passwd, *repeat; gchar *text1, *text2; gint result; dialog = gtk_dialog_new_with_buttons( _("Enter a New Password"), GTK_WINDOW(parent), GTK_DIALOG_MODAL, GTK_STOCK_OK, GTK_RESPONSE_OK, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, NULL); gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_OK); gtk_window_set_resizable(GTK_WINDOW(dialog), FALSE); hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), hbox, FALSE, FALSE, 0); passwd = gtk_label_new(_("Password: ")); gtk_box_pack_start(GTK_BOX(hbox), passwd, FALSE, FALSE, 0); passwd = gtk_entry_new(); gtk_entry_set_activates_default(GTK_ENTRY(passwd), TRUE); gtk_entry_set_visibility(GTK_ENTRY(passwd), FALSE); gtk_box_pack_start(GTK_BOX(hbox), passwd, TRUE, TRUE, 0); hbox = gtk_hbox_new(FALSE, 0); gtk_box_pack_start(GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))), hbox, FALSE, FALSE, 0); repeat = gtk_label_new(_("Repeat: ")); gtk_box_pack_start(GTK_BOX(hbox), repeat, FALSE, FALSE, 0); repeat = gtk_entry_new(); gtk_entry_set_visibility(GTK_ENTRY(repeat), FALSE); gtk_box_pack_start(GTK_BOX(hbox), repeat, TRUE, TRUE, 0); gtk_widget_show_all(dialog); text1 = text2 = NULL; //并无多大用处,主要用来避免编译警告 mark: switch (result = gtk_dialog_run(GTK_DIALOG(dialog))) { case GTK_RESPONSE_OK: text1 = gtk_editable_get_chars(GTK_EDITABLE(passwd), 0, -1); text2 = gtk_editable_get_chars(GTK_EDITABLE(repeat), 0, -1); gtk_widget_grab_focus(passwd); if (strcmp(text1, text2) != 0) { pop_warning(dialog, _("\nPassword Mismatched!")); g_free(text1); g_free(text2); goto mark; } else if (*text1 == '\0') { pop_warning(dialog, _("\nEmpty Password!")); g_free(text1); g_free(text2); goto mark; } default: break; } gtk_widget_destroy(dialog); if (result == GTK_RESPONSE_OK) { g_free(text1); return text2; } return NULL; } /** * 弹出接收文件存放位置的对话框. * @param parent parent window * @return path string */ const char *pop_save_path(GtkWidget *parent) { const char *path; GtkWidget *dialog; dialog = gtk_file_chooser_dialog_new( _("Please select a folder to save files."), GTK_WINDOW(parent), GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT, NULL); gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog), g_progdt->path.c_str()); path = g_progdt->path.c_str(); if (gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) { path = gtk_file_chooser_get_current_folder(GTK_FILE_CHOOSER(dialog)); } gtk_widget_destroy(dialog); return path; } } // namespace iptuxiptux-0.7.4/src/iptux/dialog.h000066400000000000000000000010141323207530100162330ustar00rootroot00000000000000// // C++ Interface: dialog // // Description: // 常见对话框构建 // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_DIALOG_H #define IPTUX_DIALOG_H #include "iptux/mess.h" namespace iptux { bool pop_request_quit(); bool pop_request_shared_file(PalInfo *pal); char *pop_obtain_shared_passwd(PalInfo *pal); char *pop_password_settings(GtkWidget *parent); const char *pop_save_path(GtkWidget *parent); } // namespace iptux #endif iptux-0.7.4/src/iptux/global.h000066400000000000000000000006071323207530100162430ustar00rootroot00000000000000#ifndef IPTUX_GLOBAL_H #define IPTUX_GLOBAL_H #include "iptux/CoreThread.h" #include "iptux/LogSystem.h" #include "iptux/MainWindow.h" #include "iptux/ProgramData.h" #include "iptux/SoundSystem.h" namespace iptux { extern ProgramData* g_progdt; extern CoreThread* g_cthrd; extern MainWindow* g_mwin; extern SoundSystem* g_sndsys; extern LogSystem* g_lgsys; } // namespace iptux #endif iptux-0.7.4/src/iptux/ipmsg.h000066400000000000000000000154651323207530100161320ustar00rootroot00000000000000/* * Copyright (C) 2006 Takeharu KATO * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ #if !defined(IPTUX_IPMSG_H) #define IPTUX_IPMSG_H #define IPMSG_VERSION 0x001 #define IPMSG_PORT 0x979 /* command */ #define IPMSG_NOOPERATION 0x00000000UL #define IPMSG_BR_ENTRY 0x00000001UL #define IPMSG_BR_EXIT 0x00000002UL #define IPMSG_ANSENTRY 0x00000003UL #define IPMSG_BR_ABSENCE 0x00000004UL #define IPMSG_BR_ISGETLIST 0x00000010UL #define IPMSG_OKGETLIST 0x00000011UL #define IPMSG_GETLIST 0x00000012UL #define IPMSG_ANSLIST 0x00000013UL #define IPMSG_BR_ISGETLIST2 0x00000018UL #define IPMSG_SENDMSG 0x00000020UL #define IPMSG_RECVMSG 0x00000021UL #define IPMSG_READMSG 0x00000030UL #define IPMSG_DELMSG 0x00000031UL #define IPMSG_ANSREADMSG 0x00000032UL #define IPMSG_GETINFO 0x00000040UL #define IPMSG_SENDINFO 0x00000041UL #define IPMSG_GETABSENCEINFO 0x00000050UL #define IPMSG_SENDABSENCEINFO 0x00000051UL #define IPMSG_GETFILEDATA 0x00000060UL #define IPMSG_RELEASEFILES 0x00000061UL #define IPMSG_GETDIRFILES 0x00000062UL #define IPMSG_GETPUBKEY 0x00000072UL #define IPMSG_ANSPUBKEY 0x00000073UL /* option for all command */ #define IPMSG_ABSENCEOPT 0x00000100UL #define IPMSG_SERVEROPT 0x00000200UL #define IPMSG_DIALUPOPT 0x00010000UL #define IPMSG_FILEATTACHOPT 0x00200000UL #define IPMSG_ENCRYPTOPT 0x00400000UL #define IPMSG_UTF8OPT 0x00800000UL /* option for send command */ #define IPMSG_SENDCHECKOPT 0x00000100UL #define IPMSG_SECRETOPT 0x00000200UL #define IPMSG_BROADCASTOPT 0x00000400UL #define IPMSG_MULTICASTOPT 0x00000800UL #define IPMSG_NOPOPUPOPT 0x00001000UL #define IPMSG_AUTORETOPT 0x00002000UL #define IPMSG_RETRYOPT 0x00004000UL #define IPMSG_PASSWORDOPT 0x00008000UL #define IPMSG_NOLOGOPT 0x00020000UL #define IPMSG_NEWMUTIOPT 0x00040000UL #define IPMSG_NOADDLISTOPT 0x00080000UL #define IPMSG_READCHECKOPT 0x00100000UL #define IPMSG_SECRETEXOPT (IPMSG_READCHECKOPT | IPMSG_SECRETOPT) #define IPMSG_NO_REPLY_OPTS (IPMSG_BROADCASTOPT | IPMSG_AUTORETOPT) /* encryption flags for encrypt command */ #define IPMSG_RSA_512 0x00000001UL #define IPMSG_RSA_1024 0x00000002UL #define IPMSG_RSA_2048 0x00000004UL #define IPMSG_RC2_40 0x00001000UL #define IPMSG_RC2_128 0x00004000UL #define IPMSG_RC2_256 0x00008000UL #define IPMSG_BLOWFISH_128 0x00020000UL #define IPMSG_BLOWFISH_256 0x00040000UL #define IPMSG_AES_128 0x00100000UL #define IPMSG_AES_192 0x00200000UL #define IPMSG_AES_256 0x00400000UL #define IPMSG_SIGN_STAMPOPT 0x01000000UL #define IPMSG_SIGN_MD5 0x10000000UL #define IPMSG_SIGN_SHA1 0x20000000UL /* compatibility for Win beta version */ #define IPMSG_RC2_40OLD 0x00000010UL // for beta1-4 only #define IPMSG_RC2_128OLD 0x00000040UL // for beta1-4 only #define IPMSG_BLOWFISH_128OLD 0x00000400UL // for beta1-4 only #define IPMSG_RC2_40ALL (IPMSG_RC2_40 | IPMSG_RC2_40OLD) #define IPMSG_RC2_128ALL (IPMSG_RC2_128 | IPMSG_RC2_128OLD) #define IPMSG_BLOWFISH_128ALL (IPMSG_BLOWFISH_128 | IPMSG_BLOWFISH_128OLD) /* file types for fileattach command */ #define IPMSG_FILE_REGULAR 0x00000001UL #define IPMSG_FILE_DIR 0x00000002UL #define IPMSG_FILE_RETPARENT 0x00000003UL // return parent directory #define IPMSG_FILE_SYMLINK 0x00000004UL #define IPMSG_FILE_CDEV 0x00000005UL // for UNIX #define IPMSG_FILE_BDEV 0x00000006UL // for UNIX #define IPMSG_FILE_FIFO 0x00000007UL // for UNIX #define IPMSG_FILE_RESFORK 0x00000010UL // for Mac /* file attribute options for fileattach command */ #define IPMSG_FILE_RONLYOPT 0x00000100UL #define IPMSG_FILE_HIDDENOPT 0x00001000UL #define IPMSG_FILE_EXHIDDENOPT 0x00002000UL // for MacOS X #define IPMSG_FILE_ARCHIVEOPT 0x00004000UL #define IPMSG_FILE_SYSTEMOPT 0x00008000UL /* extend attribute types for fileattach command */ #define IPMSG_FILE_UID 0x00000001UL #define IPMSG_FILE_USERNAME 0x00000002UL // uid by string #define IPMSG_FILE_GID 0x00000003UL #define IPMSG_FILE_GROUPNAME 0x00000004UL // gid by string #define IPMSG_FILE_PERM 0x00000010UL // for UNIX #define IPMSG_FILE_MAJORNO 0x00000011UL // for UNIX devfile #define IPMSG_FILE_MINORNO 0x00000012UL // for UNIX devfile #define IPMSG_FILE_CTIME 0x00000013UL // for UNIX #define IPMSG_FILE_MTIME 0x00000014UL #define IPMSG_FILE_ATIME 0x00000015UL #define IPMSG_FILE_CREATETIME 0x00000016UL #define IPMSG_FILE_CREATOR 0x00000020UL // for Mac #define IPMSG_FILE_FILETYPE 0x00000021UL // for Mac #define IPMSG_FILE_FINDERINFO 0x00000022UL // for Mac #define IPMSG_FILE_ACL 0x00000030UL #define IPMSG_FILE_ALIASFNAME 0x00000040UL // alias fname #define IPMSG_FILE_UNICODEFNAME 0x00000041UL // UNICODE fname #define HLIST_ENTRY_SEPARATOR ':' /* macro */ #define GET_MODE(command) ((command)&0x000000ffUL) #define GET_OPT(command) ((command)&0xffffff00UL) /* header */ #define IPTUX_DEFAULT_PORT IPMSG_PORT /* command */ #define IPTUX_ASKSHARED 0x000000FFUL #define IPTUX_SENDICON 0x000000FEUL #define IPTUX_SENDSUBLAYER 0x000000FDUL #define IPTUX_SENDSIGN 0x000000FCUL #define IPTUX_SENDMSG 0x000000FBUL /* option for IPTUX_SENDSUBLAYER */ #define IPTUX_PHOTOPICOPT 0x00000100UL #define IPTUX_MSGPICOPT 0x00000200UL /* option for IPMSG_SENDMSG */ #define IPTUX_SHAREDOPT 0x80000000UL /* option for IPMSG_SENDMSG & IPTUX_ASKSHARED */ #define IPTUX_PASSWDOPT 0x40000000UL /* option for IPTUX_SENDMSG */ #define IPTUX_REGULAROPT 0x00000100UL #define IPTUX_SEGMENTOPT 0x00000200UL #define IPTUX_GROUPOPT 0x00000300UL #define IPTUX_BROADCASTOPT 0x00000400UL /* data */ #define MAX_SOCKLEN 8192 #define MAX_UDPLEN 8192 #define MAX_BUFLEN 1024 #define MAX_PATHLEN 1024 #define MAX_SHAREDFILE 10000 #define MAX_ICONSIZE 30 #define MAX_PREVIEWSIZE 150 #define MAX_PHOTOSIZE 300 #define MAX_RETRYTIMES 4 #endif iptux-0.7.4/src/iptux/mess.cpp000066400000000000000000000045661323207530100163150ustar00rootroot00000000000000// // C++ Implementation: mess // // Description: // // // Author: Jally , (C) 2009 // // Copyright: See COPYING file that comes with this distribution // // #include "mess.h" #include "iptux/utils.h" namespace iptux { PalInfo::PalInfo() : ipv4(0), segdes(NULL), version(NULL), user(NULL), host(NULL), name(NULL), group(NULL), photo(NULL), sign(NULL), iconfile(NULL), encode(NULL), flags(0), packetn(0), rpacketn(0) {} PalInfo::~PalInfo() { g_free(segdes); g_free(version); g_free(user); g_free(host); g_free(name); g_free(group); g_free(photo); g_free(sign); g_free(iconfile); g_free(encode); } GroupInfo::GroupInfo() : grpid(0), type(GROUP_BELONG_TYPE_REGULAR), name(NULL), member(NULL), buffer(NULL), dialog(NULL) {} GroupInfo::~GroupInfo() { g_free(name); g_slist_free(member); g_object_unref(buffer); } FileInfo::FileInfo() : fileid(0), packetn(0), fileattr(0), filesize(-1), finishedsize(0), fileown(NULL), filepath(NULL) {} FileInfo::~FileInfo() { g_free(filepath); } MsgPara::MsgPara() : pal(NULL), stype(MESSAGE_SOURCE_TYPE_PAL), btype(GROUP_BELONG_TYPE_REGULAR), dtlist(NULL) {} MsgPara::~MsgPara() { for (GSList* tlist = dtlist; tlist; tlist = g_slist_next(tlist)) delete (ChipData*)tlist->data; g_slist_free(dtlist); } ChipData::ChipData() : type(MESSAGE_CONTENT_TYPE_STRING), data(NULL) {} ChipData::~ChipData() { g_free(data); } NetSegment::NetSegment() : startip(NULL), endip(NULL), description(NULL) {} NetSegment::~NetSegment() { g_free(startip); g_free(endip); g_free(description); } Json::Value NetSegment::ToJsonValue() const { Json::Value value; value["startip"] = startip; value["endip"] = endip; value["description"] = description; return value; } // static NetSegment* NetSegment::NewFromJsonValue(const Json::Value& value) { NetSegment* res = new NetSegment(); res->startip = g_strdup(value["startip"].asString().c_str()); res->endip = g_strdup(value["startip"].asString().c_str()); res->description = g_strdup(value["startip"].asString().c_str()); return res; } SessionAbstract::SessionAbstract() {} SessionAbstract::~SessionAbstract() {} TransAbstract::TransAbstract() {} TransAbstract::~TransAbstract() {} } // namespace iptuxiptux-0.7.4/src/iptux/mess.h000066400000000000000000000117761323207530100157630ustar00rootroot00000000000000// // C++ Interface: mess // // Description: // 很杂乱的一些数据基本结构. // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_MESS_H #define IPTUX_MESS_H #include #include #include namespace iptux { /** * 消息来源类型. */ typedef enum { MESSAGE_SOURCE_TYPE_PAL, ///< 好友 MESSAGE_SOURCE_TYPE_SELF, ///< 自身 MESSAGE_SOURCE_TYPE_ERROR ///< 错误 } MessageSourceType; /** * 消息内容类型. */ typedef enum { MESSAGE_CONTENT_TYPE_STRING, ///< 字符串 MESSAGE_CONTENT_TYPE_PICTURE ///< 图片 } MessageContentType; /** * 群组所属类型 */ typedef enum { GROUP_BELONG_TYPE_REGULAR, ///< 常规 GROUP_BELONG_TYPE_SEGMENT, ///< 分段 GROUP_BELONG_TYPE_GROUP, ///< 分组 GROUP_BELONG_TYPE_BROADCAST ///< 广播 } GroupBelongType; /***************偶是可爱的分割线(数据对象)*****************/ /** * 好友信息. * flags位含义: \n * 黑名单(:3);此IP地址被列入黑名单(deprecated) \n * 更改(:2);好友的信息被用户手工修改,程序不应再更改好友的信息 \n * 在线(:1);好友依旧在线 \n * 兼容(:0);完全兼容iptux,程序将采用扩展协议与好友通信 \n */ class PalInfo { public: PalInfo(); ~PalInfo(); in_addr_t ipv4; ///< 好友IP char *segdes; ///< 所在网段描述 char *version; ///< 版本串 * char *user; ///< 好友用户 * char *host; ///< 好友主机 * char *name; ///< 昵称 * char *group; ///< 所在群组 char *photo; ///< 形象照片 char *sign; ///< 个性签名 char *iconfile; ///< 好友头像 * char *encode; ///< 好友编码 * uint8_t flags; ///< 3 黑名单:2 更改:1 在线:0 兼容 uint32_t packetn; ///< 已接受最大的包编号 uint32_t rpacketn; ///< 需要接受检查的包编号 }; /** * 群组信息. */ class GroupInfo { public: GroupInfo(); ~GroupInfo(); GQuark grpid; ///< 唯一标识 GroupBelongType type; ///< 群组类型 char *name; ///< 群组名称 * GSList *member; ///< 群组成员(数据不为本链表拥有) GtkTextBuffer *buffer; ///< 消息缓冲区 * GtkWidget *dialog; ///< 对话框(若存在则必须与对话框类关联) }; /** * 文件信息. */ class FileInfo { public: FileInfo(); ~FileInfo(); uint32_t fileid; ///< 唯一标识 uint32_t packetn; ///< 包编号 uint32_t fileattr; ///< 文件属性 int64_t filesize; ///< 文件大小 int64_t finishedsize; ///< 已完成大小 PalInfo *fileown; ///< 文件拥有者(来自好友*) char *filepath; ///< 文件路径 * uint32_t filectime; ///< 文件创建时间 uint32_t filemtime; ///< 文件最后修改时间 uint32_t filenum; ///< 包内编号 }; /** * 消息参数. */ class MsgPara { public: MsgPara(); ~MsgPara(); PalInfo *pal; ///< 好友数据信息(来自好友*) MessageSourceType stype; ///< 来源类型 GroupBelongType btype; ///< 所属类型 GSList *dtlist; ///< 数据链表 * }; /** * 碎片数据. */ class ChipData { public: ChipData(); ~ChipData(); MessageContentType type; ///< 消息内容类型 char *data; ///< 数据串 * }; /** * 网段数据. */ class NetSegment { public: NetSegment(); ~NetSegment(); char *startip; ///< IP起始地址 * char *endip; ///< IP终止地址 * char *description; ///< 此IP段描述 Json::Value ToJsonValue() const; static NetSegment *NewFromJsonValue(const Json::Value &value); }; /***************偶是可爱的分割线(抽象类)*****************/ /** * 会话抽象类. * 提供好友会话类必需的公共接口. */ class SessionAbstract { public: SessionAbstract(); virtual ~SessionAbstract(); virtual void UpdatePalData(PalInfo *pal) = 0; ///< 更新好友数据 virtual void InsertPalData(PalInfo *pal) = 0; ///< 插入好友数据 virtual void DelPalData(PalInfo *pal) = 0; ///< 删除好友数据 virtual void ClearAllPalData() = 0; ///< 清除所有好友数据 // virtual void ShowEnclosure() = 0; ///< 显示附件 virtual void AttachEnclosure(const GSList *list) = 0; ///< 添加附件 virtual void OnNewMessageComing() = 0; ///< 窗口打开情况下有新消息 }; /** * 传输抽象类. * 提供文件传输类必需的公共接口. */ class TransAbstract { public: TransAbstract(); virtual ~TransAbstract(); /** * GData数据如下: \n * [GdkPixbuf]status, [gchar]task, [gchar]peer, [gchar]filename, * [gchar]filelength, [gchar]finishlength, [gint]progress, [gchar]pro-text, * [gchar]cost, [gchar]remain, [gchar]rate, [gpointer]data \n * @see MainWindow::CreateTransModel() */ virtual GData **GetTransFilePara() = 0; ///< 获取更新UI的数据 virtual void TerminateTrans() = 0; ///< 终止过程处理 }; } // namespace iptux #endif iptux-0.7.4/src/iptux/output.cpp000066400000000000000000000052671323207530100167050ustar00rootroot00000000000000// // C++ Implementation: output // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "output.h" #include #include "iptux/deplib.h" using namespace std; namespace iptux { /** * 弹出消息提示. * @param parent parent window * @param format as in printf() * @param ... */ void pop_info(GtkWidget *parent, const gchar *format, ...) { GtkWidget *dialog; gchar *msg; va_list ap; va_start(ap, format); msg = g_strdup_vprintf(format, ap); va_end(ap); dialog = gtk_message_dialog_new(GTK_WINDOW(parent), GTK_DIALOG_MODAL, GTK_MESSAGE_INFO, GTK_BUTTONS_OK, NULL); gtk_message_dialog_set_markup(GTK_MESSAGE_DIALOG(dialog), msg); g_free(msg); gtk_window_set_title(GTK_WINDOW(dialog), _("Information")); gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); } /** * 弹出警告信息. * @param parent parent window * @param format as in printf() * @param ... */ void pop_warning(GtkWidget *parent, const gchar *format, ...) { GtkWidget *dialog; gchar *msg; va_list ap; va_start(ap, format); msg = g_strdup_vprintf(format, ap); va_end(ap); dialog = gtk_message_dialog_new(GTK_WINDOW(parent), GTK_DIALOG_MODAL, GTK_MESSAGE_INFO, GTK_BUTTONS_OK, NULL); gtk_message_dialog_set_markup(GTK_MESSAGE_DIALOG(dialog), msg); g_free(msg); gtk_window_set_title(GTK_WINDOW(dialog), _("Warning")); gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); } /** * 严重错误,程序将有可能自行强制退出. * @param format as in printf() * @param ... */ void pop_error(const gchar *format, ...) { GtkWidget *dialog; gchar *msg; va_list ap; va_start(ap, format); msg = g_strdup_vprintf(format, ap); va_end(ap); dialog = gtk_message_dialog_new(NULL, GTK_DIALOG_MODAL, GTK_MESSAGE_INFO, GTK_BUTTONS_OK, NULL); gtk_message_dialog_set_markup(GTK_MESSAGE_DIALOG(dialog), msg); g_free(msg); gtk_window_set_title(GTK_WINDOW(dialog), _("Error")); gtk_dialog_run(GTK_DIALOG(dialog)); gtk_widget_destroy(dialog); } string pretty_fname(const string &fname) { size_t pos = fname.rfind("/src/"); if (pos == string::npos) { return fname; } else { return fname.substr(pos + 5); } } void DoLog(const char *fname, int line, const char *func, GLogLevelFlags level, const char *format, ...) { va_list ap; va_start(ap, format); gchar *msg = g_strdup_vprintf(format, ap); va_end(ap); g_log("iptux", level, "%s:%d:%s:%s", pretty_fname(fname).c_str(), line, func, msg); g_free(msg); } } // namespace iptux iptux-0.7.4/src/iptux/output.h000066400000000000000000000027551323207530100163510ustar00rootroot00000000000000// // C++ Interface: output // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_OUTPUT_H #define IPTUX_OUTPUT_H #include namespace iptux { #define LOG_DEBUG(format, ...) \ DoLog(__FILE__, __LINE__, __func__, G_LOG_LEVEL_DEBUG, (format), \ ##__VA_ARGS__) #define LOG_INFO(format, ...) \ DoLog(__FILE__, __LINE__, __func__, G_LOG_LEVEL_INFO, (format), ##__VA_ARGS__) #define LOG_WARN(format, ...) \ DoLog(__FILE__, __LINE__, __func__, G_LOG_LEVEL_WARNING, (format), \ ##__VA_ARGS__) #define LOG_CRIT(format, ...) \ DoLog(__FILE__, __LINE__, __func__, G_LOG_LEVEL_CRITICAL, (format), \ ##__VA_ARGS__) #define LOG_ERROR(format, ...) \ DoLog(__FILE__, __LINE__, __func__, G_LOG_LEVEL_ERROR, (format), \ ##__VA_ARGS__) /* 警告信息输出 */ #ifndef WARNING #define pwarning(format, ...) /*warnx(format,##__VA_ARGS__)*/ #else #define pwarning(format, ...) warnx(format, ##__VA_ARGS__) #endif void DoLog(const char *fname, int line, const char *func, GLogLevelFlags level, const char *format, ...); void pop_info(GtkWidget *parent, const gchar *format, ...); void pop_warning(GtkWidget *parent, const gchar *format, ...); void pop_error(const gchar *format, ...); } // namespace iptux #endif iptux-0.7.4/src/iptux/support.cpp000066400000000000000000000255001323207530100170510ustar00rootroot00000000000000// // C++ Implementation: support // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "support.h" #include #include #include #include "CoreThread.h" #include "LogSystem.h" #include "MainWindow.h" #include "ProgramData.h" #include "SoundSystem.h" #include "dialog.h" #include "global.h" #include "ipmsg.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "output.h" #include "utils.h" namespace iptux { static void bind_iptux_port(int port); /** * 程序必要初始化. */ void iptux_init(int port) { bind_iptux_port(port); init_iptux_environment(); g_progdt->InitSublayer(); g_lgsys->InitSublayer(); g_sndsys->InitSublayer(); signal(SIGPIPE, SIG_IGN); signal(SIGHUP, iptux_quit); signal(SIGINT, iptux_quit); signal(SIGQUIT, iptux_quit); signal(SIGTERM, iptux_quit); g_lgsys->SystemLog(_("Loading the process successfully!")); } /** * 程序GUI退出. */ void iptux_gui_quit() { if (g_mwin->TransmissionActive() && !pop_request_quit()) return; gtk_main_quit(); iptux_quit(0); } /** * 程序底层退出. */ void iptux_quit(int _ignore) { g_lgsys->SystemLog(_("The process is about to quit!")); exit(0); } /** * 打开URL. * @param url url */ void iptux_open_url(const char *url) { int fd; if (fork() != 0) return; /* 关闭由iptux打开的所有可能的文件描述符 */ fd = 3; while (fd < FD_SETSIZE) { close(fd); fd++; } /* 脱离终端控制 */ setsid(); /* 打开URL */ execlp("xdg-open", "xdg-open", url, NULL); /* 测试系统中所有可能被安装的浏览器 */ execlp("firefox", "firefox", url, NULL); execlp("opera", "opera", url, NULL); execlp("konqueror", "konqueror", url, NULL); execlp("open", "open", url, NULL); pwarning(_("Can't find any available web browser!\n")); } /** * 绑定iptux程序的服务监听端口. */ void bind_iptux_port(int port) { struct sockaddr_in addr; int tcpsock, udpsock; tcpsock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); socket_enable_reuse(tcpsock); udpsock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); socket_enable_reuse(udpsock); socket_enable_broadcast(udpsock); if ((tcpsock == -1) || (udpsock == -1)) { g_warning(_("Fatal Error!! Failed to create new socket!\n%s"), strerror(errno)); pop_warning(NULL, _("Fatal Error!!\nFailed to create new socket!\n%s"), strerror(errno)); exit(1); } bzero(&addr, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_port = htons(port); addr.sin_addr.s_addr = htonl(INADDR_ANY); if (bind(tcpsock, (struct sockaddr *)&addr, sizeof(addr)) == -1 || bind(udpsock, (struct sockaddr *)&addr, sizeof(addr)) == -1) { close(tcpsock); close(udpsock); g_warning(_("Fatal Error!! Failed to bind the TCP/UDP port(%d)!\n%s"), port, strerror(errno)); pop_warning(NULL, _("Fatal Error!!\nFailed to bind the TCP/UDP port(%d)!\n%s"), port, strerror(errno)); exit(1); } g_cthrd->TcpSockQuote() = tcpsock; g_cthrd->UdpSockQuote() = udpsock; } /** * 初始化程序iptux的运行环境. * cache iptux {pic, photo, icon} \n * config iptux {log, photo, icon} \n */ void init_iptux_environment() { const char *env; char path[MAX_PATHLEN]; env = g_get_user_cache_dir(); if (access(env, F_OK) != 0) mkdir(env, 0777); snprintf(path, MAX_PATHLEN, "%s" IPTUX_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" PIC_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" LOG_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); env = g_get_user_config_dir(); if (access(env, F_OK) != 0) mkdir(env, 0777); snprintf(path, MAX_PATHLEN, "%s" IPTUX_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" LOG_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" PHOTO_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" ICON_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); snprintf(path, MAX_PATHLEN, "%s" LOG_PATH, env); if (access(path, F_OK) != 0) mkdir(path, 0777); } /** * 按照1:1的比例对图片做缩小(请注意,没有放大)处理. * @param pixbuf pixbuf * @param width width * @param height height * @note 原pixbuf将被本函数释放 */ void pixbuf_shrink_scale_1(GdkPixbuf **pixbuf, int width, int height) { gdouble scale_x, scale_y, scale; gint _width, _height; GdkPixbuf *tpixbuf; width = (width != -1) ? width : G_MAXINT; height = (height != -1) ? height : G_MAXINT; _width = gdk_pixbuf_get_width(*pixbuf); _height = gdk_pixbuf_get_height(*pixbuf); if (_width > width || _height > height) { scale = ((scale_x = (gdouble)width / _width) < (scale_y = (gdouble)height / _height)) ? scale_x : scale_y; _width = (gint)(_width * scale); _height = (gint)(_height * scale); tpixbuf = *pixbuf; *pixbuf = gdk_pixbuf_scale_simple(tpixbuf, _width, _height, GDK_INTERP_BILINEAR); g_object_unref(tpixbuf); } } /** * 获取库存图片. * @param stock_id a stock ID * @return pixbuf */ GdkPixbuf *obtain_pixbuf_from_stock(const gchar *stock_id) { GtkWidget *widget; GdkPixbuf *pixbuf; widget = gtk_window_new(GTK_WINDOW_TOPLEVEL); pixbuf = gtk_widget_render_icon(widget, stock_id, GTK_ICON_SIZE_MENU, NULL); gtk_widget_destroy(widget); return pixbuf; } /** * 让窗体(widget)支持uri拖拽操作. * @param widget widget */ void widget_enable_dnd_uri(GtkWidget *widget) { static const GtkTargetEntry target = {(gchar *)"text/uri-list", 0, 0}; gtk_drag_dest_set(widget, GTK_DEST_DEFAULT_ALL, &target, 1, GDK_ACTION_MOVE); } /** * 由(GtkSelectionData)获取(uri)文件链表. * @param data selection data * @return 文件链表 */ GSList *selection_data_get_path(GtkSelectionData *data) { const char *prl = "file://"; gchar **uris, **ptr, *uri; GSList *filelist; if (!(uris = gtk_selection_data_get_uris(data))) return NULL; filelist = NULL; ptr = uris; while (*ptr) { uri = g_uri_unescape_string(*ptr, NULL); if (strncasecmp(uri, prl, strlen(prl)) == 0) filelist = g_slist_append(filelist, g_strdup(uri + strlen(prl))); else filelist = g_slist_append(filelist, g_strdup(uri)); g_free(uri); ptr++; } g_strfreev(uris); return filelist; } /** * 获取局域网网段名称. * @param ipv4 ipv4 * @return name */ char *ipv4_get_lan_name(in_addr_t ipv4) { /** * @note 局域网网段划分,每两个为一组,以NULL标识结束. */ const char *localgroup[] = { "10.0.0.0", "10.255.255.255", "172.16.0.0", "172.31.255.255", "192.168.0.0", "192.168.255.255", NULL}; in_addr_t startip, endip; uint8_t count; char *ipstr; ipv4 = ntohl(ipv4); ipstr = NULL; count = 0; while (localgroup[count << 1]) { inet_pton(AF_INET, localgroup[count << 1], &startip); startip = ntohl(startip); inet_pton(AF_INET, localgroup[(count << 1) + 1], &endip); endip = ntohl(endip); ipv4_order(&startip, &endip); if (startip <= ipv4 && endip >= ipv4) { ipstr = g_strdup_printf("%s~%s", localgroup[count << 1], localgroup[(count << 1) + 1]); break; } count++; } return ipstr; } /** * 让套接口支持广播. * @param sock socket */ void socket_enable_broadcast(int sock) { socklen_t len; int optval; optval = 1; len = sizeof(optval); setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &optval, len); } /** * 让套接口监听端口可重用. * @param sock socket */ void socket_enable_reuse(int sock) { socklen_t len; int optval; optval = 1; len = sizeof(optval); setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &optval, len); } /** * 获取系统主机的广播地址. * @param sock socket * @return 广播地址链表 * @note 链表数据不是指针而是实际的IP */ GSList *get_sys_broadcast_addr(int sock) { const uint8_t amount = 5; //支持5个IP地址 uint8_t count, sum; struct ifconf ifc; struct ifreq *ifr; struct sockaddr_in *addr; GSList *list; list = g_slist_append(NULL, GUINT_TO_POINTER(inet_addr("255.255.255.255"))); ifc.ifc_len = amount * sizeof(struct ifreq); ifc.ifc_buf = (caddr_t)g_malloc(ifc.ifc_len); if (ioctl(sock, SIOCGIFCONF, &ifc) == -1) { g_free(ifc.ifc_buf); return list; } sum = ifc.ifc_len / sizeof(struct ifreq); count = 0; while (count < sum) { ifr = ifc.ifc_req + count; count++; if (ioctl(sock, SIOCGIFFLAGS, ifr) == -1 || !(ifr->ifr_flags & IFF_BROADCAST) || ioctl(sock, SIOCGIFBRDADDR, ifr) == -1) continue; addr = (struct sockaddr_in *)&ifr->ifr_broadaddr; list = g_slist_append(list, GUINT_TO_POINTER(addr->sin_addr.s_addr)); } g_free(ifc.ifc_buf); return list; } /** * 获取系统主机的IP地址. * @param sock socket * @return IP地址链表 * @note 链表数据不是指针而是实际的IP */ GSList *get_sys_host_addr(int sock) { const uint8_t amount = 5; //支持5个IP地址 uint8_t count, sum; struct ifconf ifc; struct ifreq *ifr; struct sockaddr_in *addr; GSList *list; list = NULL; ifc.ifc_len = amount * sizeof(struct ifreq); ifc.ifc_buf = (caddr_t)g_malloc(ifc.ifc_len); if (ioctl(sock, SIOCGIFCONF, &ifc) == -1) { g_free(ifc.ifc_buf); return list; } sum = ifc.ifc_len / sizeof(struct ifreq); count = 0; while (count < sum) { ifr = ifc.ifc_req + count; count++; if (strncasecmp(ifr->ifr_name, "lo", 2) == 0 || ioctl(sock, SIOCGIFFLAGS, ifr) == -1 || !(ifr->ifr_flags & IFF_UP) || ioctl(sock, SIOCGIFADDR, ifr) == -1) continue; addr = (struct sockaddr_in *)&ifr->ifr_broadaddr; list = g_slist_append(list, GUINT_TO_POINTER(addr->sin_addr.s_addr)); } g_free(ifc.ifc_buf); return list; } /** * 获取系统主机的IP地址串描述 * @param sock socket * @return 描述串 */ char *get_sys_host_addr_string(int sock) { char ipstr[INET_ADDRSTRLEN], *buf, *ptr; GSList *list, *tlist; uint16_t len; if (!(tlist = list = get_sys_host_addr(sock))) return NULL; len = g_slist_length(list) * INET_ADDRSTRLEN; ptr = buf = (char *)g_malloc(len); while (tlist) { inet_ntop(AF_INET, &tlist->data, ipstr, INET_ADDRSTRLEN); snprintf(ptr, len, "%s\n", ipstr); ptr += strlen(ptr); len -= INET_ADDRSTRLEN; tlist = g_slist_next(tlist); } *(ptr - 1) = '\0'; //抹除最后一个换行符 g_slist_free(list); return buf; } } // namespace iptux iptux-0.7.4/src/iptux/support.h000066400000000000000000000016231323207530100165160ustar00rootroot00000000000000// // C++ Interface: support // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_SUPPORT_H #define IPTUX_SUPPORT_H #include "iptux/mess.h" namespace iptux { void iptux_init(int port); void iptux_gui_quit(); void iptux_quit(int); void iptux_open_url(const char *url); void init_iptux_environment(); void pixbuf_shrink_scale_1(GdkPixbuf **pixbuf, int width, int height); GdkPixbuf *obtain_pixbuf_from_stock(const gchar *stock_id); void widget_enable_dnd_uri(GtkWidget *widget); GSList *selection_data_get_path(GtkSelectionData *data); char *ipv4_get_lan_name(in_addr_t ipv4); void socket_enable_broadcast(int sock); void socket_enable_reuse(int sock); GSList *get_sys_broadcast_addr(int sock); GSList *get_sys_host_addr(int sock); char *get_sys_host_addr_string(int sock); } // namespace iptux #endif iptux-0.7.4/src/iptux/utils.cpp000066400000000000000000000336231323207530100165020ustar00rootroot00000000000000// // C++ Implementation: utils // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "utils.h" #ifndef __APPLE__ #include #endif #include #include #include #include "iptux/ipmsg.h" using namespace std; namespace iptux { /** * 对两个主机序的ipv4地址进行排序. * @param ip1 ipv4(host byte order) * @param ip2 ipv4(host byte order) */ void ipv4_order(in_addr_t *ip1, in_addr_t *ip2) { in_addr_t ip; if (*ip1 > *ip2) { ip = *ip1; *ip1 = *ip2; *ip2 = ip; } } /** * 检查串(string)是否为有效的utf8串,若不是则根据字符集(codeset)来进行转码. * @param string 待检查的字符串 * @param codeset 字符集编码,e.g. * @retval encode 正确的字符集编码由此返回 * @return 有效的utf8串 * @note * 若(string)为utf8编码,或(codeset)中不存在(string)的正确编码,函数将返回NULL * @see iptux_string_validate_copy() */ char *iptux_string_validate(const char *s, const string &codeset, char **encode) { const char *pptr, *ptr; char *tstring, *cset; gsize rbytes, wbytes; *encode = NULL; //设置字符集编码未知 tstring = NULL; //设置utf8有效串尚未成功获取 if (!g_utf8_validate(s, -1, NULL) && !codeset.empty()) { cset = NULL; ptr = codeset.c_str(); do { if (*(pptr = ptr + strspn(ptr, ",;\x20\t")) == '\0') break; if (!(ptr = strpbrk(pptr, ",;\x20\t"))) ptr = pptr + strlen(pptr); g_free(cset); cset = g_strndup(pptr, ptr - pptr); if (strcasecmp(cset, "utf-8") == 0) continue; } while ( !(tstring = g_convert(s, -1, "utf-8", cset, &rbytes, &wbytes, NULL))); *encode = cset; } return tstring; } /** * 检查串(string)是否为有效的utf8串,若不是则根据字符集(codeset)来进行转码. * @param string 待检查的字符串 * @param codeset 字符集编码,e.g. * @retval encode 正确的字符集编码由此返回 * @return 有效的utf8串 * @note 本函数无论处理结果如何,都会无条件的返回一个字符集编码以及一个新串 * @see iptux_string_validate() */ char *iptux_string_validate_copy(const char *string, const char *codeset, char **encode) { char *tstring; if (!codeset || !(tstring = iptux_string_validate(string, codeset, encode))) { *encode = g_strdup("utf-8"); tstring = g_strdup(string); } return tstring; } /** * 转换字符串编码. * @param string 字符串 * @param tocode 目标编码 * @param fromcode 源编码 * @return 新串 * @note 若函数执行出错,将返回NULL */ char *convert_encode(const char *string, const char *tocode, const char *fromcode) { gsize rbytes, wbytes; char *tstring; tstring = g_convert(string, -1, tocode, fromcode, &rbytes, &wbytes, NULL); return tstring; } /** * 转换字符串编码. * @param string 字符串 * @param tocode 目标编码 * @param fromcode 源编码 * @return 新串 * @note 无论函数处理结果如何,都将会返回一个新串 */ char *convert_encode_copy(const char *string, const char *tocode, const char *fromcode) { char *tstring; if (!(tstring = convert_encode(string, tocode, fromcode))) tstring = g_strdup(string); return tstring; } /** * 获取文件系统的存储空间信息. * @param path 文件路径 * @retval avail 可用空间由此返回 * @retval total 全部空间由此返回 */ void get_file_system_info(const char *path, int64_t *avail, int64_t *total) { #ifdef __APPLE__ *avail = *total = 0; #else struct statfs64 st; int result; mark: switch (result = statfs64(path, &st)) { case 0: *avail = (int64_t)st.f_bsize * st.f_bavail; *total = (int64_t)st.f_bsize * st.f_blocks; break; default: if (errno == EINTR) goto mark; *avail = *total = 0; break; } #endif } /** * 从字符串(str)当前位置开始提取一行数据. * @param str 字符串起始指针 * @return 从(str)开始的一行数据 * @note 首部、尾部的空白字符将会被删除 */ char *iptux_string_getline(const char *str) { const char *pptr, *ptr; char *dst; size_t len; dst = NULL; pptr = str + strspn(str, "\x20\t"); ptr = strpbrk(pptr, "\r\n"); if ((len = ptr ? (ptr - pptr) : strlen(pptr))) { dst = g_strndup(pptr, len); g_strchomp(dst); } return dst; } /** * 确保(path)所指向的文件不存在. * @param path 文件路径 * @return 新文件路径 * */ char *assert_filename_inexist(const char *path) { char buf[MAX_PATHLEN]; const char *ptr; uint16_t count; if (access(path, F_OK) != 0) return g_strdup(path); ptr = strrchr(path, '/'); ptr = ptr ? ptr + 1 : path; count = 1; while (count) { snprintf(buf, MAX_PATHLEN, "%.*s%" PRIu16 "_%s", (int)(ptr - path), path, count, ptr); if (access(buf, F_OK) != 0) break; count++; } /* 概率极低,不妨忽略错误情形 */ return g_strdup(buf); } /** * 获取包含指定数据的格式化时间串. * @param date 是否需要包含日期 * @param format as in printf() * @param ... as in printf() * @return 时间串 */ char *getformattime(gboolean date, const char *format, ...) { char buf[MAX_BUFLEN], *msg, *ptr; struct tm *tm; time_t tt; va_list ap; va_start(ap, format); msg = g_strdup_vprintf(format, ap); va_end(ap); time(&tt); tm = localtime(&tt); if (date) strftime(buf, MAX_BUFLEN, "%c", tm); else strftime(buf, MAX_BUFLEN, "%X", tm); ptr = g_strdup_printf("(%s) %s:", buf, msg); g_free(msg); return ptr; } /** * 对GtkTextBuffer的迭代器(GtkTextIter)所指的字符进行比较. * @param src 源字符 * @param dst 目标字符 * @return Gtk+库 */ gboolean giter_compare_foreach(gunichar src, gunichar dst) { return (src == dst); } /** * 把数值(numeric)转换为文件长度描述串. * @param numeric 需要转换的数值 * @return 描述串 */ char *numeric_to_size(int64_t numeric) { gchar *ptr; if (numeric >= ((int64_t)1 << 40)) ptr = g_strdup_printf("%.1fT", (float)numeric / ((int64_t)1 << 40)); else if (numeric >= (1 << 30)) ptr = g_strdup_printf("%.1fG", (float)numeric / (1 << 30)); else if (numeric >= (1 << 20)) ptr = g_strdup_printf("%.1fM", (float)numeric / (1 << 20)); else if (numeric >= (1 << 10)) ptr = g_strdup_printf("%.1fK", (float)numeric / (1 << 10)); else ptr = g_strdup_printf("%" PRId64 "B", numeric); return ptr; } /** * 把数值(numeric)转换为速度大小描述串. * @param numeric 需要转换的数值 * @return 描述串 */ char *numeric_to_rate(uint32_t numeric) { gchar *ptr; if (numeric >= (1 << 30)) ptr = g_strdup_printf("%.1fG/s", (float)numeric / (1 << 30)); else if (numeric >= (1 << 20)) ptr = g_strdup_printf("%.1fM/s", (float)numeric / (1 << 20)); else if (numeric >= (1 << 10)) ptr = g_strdup_printf("%.1fK/s", (float)numeric / (1 << 10)); else ptr = g_strdup_printf("%" PRIu32 "B/s", numeric); return ptr; } /** * 把数值(numeric)转换为时间长度描述串. * @param numeric 需要转换的数值 * @return 描述串 */ char *numeric_to_time(uint32_t numeric) { uint32_t hour, minute; gchar *ptr; hour = numeric / 3600; numeric %= 3600; minute = numeric / 60; numeric %= 60; ptr = g_strdup_printf("%.2" PRIu32 ":%.2" PRIu32 ":%.2" PRIu32, hour, minute, numeric); return ptr; } /** * 查询以(string)为起始点,(times)个字符串后的指针位置. * @param string 串起始点 * @param size 串有效长度 * @param times 跳跃次数 * @return 指针位置 */ const char *iptux_skip_string(const char *string, size_t size, uint8_t times) { const char *ptr; uint8_t count; ptr = string; count = 0; while (count < times) { ptr += strlen(ptr) + 1; if ((size_t)(ptr - string) >= size) { ptr = NULL; break; } count++; } return ptr; } /** * 查询以(string)为起始点,跳跃(times)次(ch)字符后的指针位置. * @param string 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 指针位置 */ const char *iptux_skip_section(const char *string, char ch, uint8_t times) { const char *ptr; uint8_t count; ptr = string; count = 0; while (count < times) { if (!(ptr = strchr(ptr, ch))) break; ptr++; //跳过当前分割字符 count++; } return ptr; } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的16进制数值. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 数值 */ int64_t iptux_get_hex64_number(const char *msg, char ch, uint8_t times) { const char *ptr; int64_t number; if (!(ptr = iptux_skip_section(msg, ch, times))) return 0; if (sscanf(ptr, "%" SCNx64, &number) == 1) return number; return 0; } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的16进制数值. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 数值 */ uint32_t iptux_get_hex_number(const char *msg, char ch, uint8_t times) { const char *ptr; uint32_t number; if (!(ptr = iptux_skip_section(msg, ch, times))) return 0; if (sscanf(ptr, "%" SCNx32, &number) == 1) return number; return 0; } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的10进制数值. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 数值 */ uint32_t iptux_get_dec_number(const char *msg, char ch, uint8_t times) { const char *ptr; uint32_t number; if (!(ptr = iptux_skip_section(msg, ch, times))) return 0; if (sscanf(ptr, "%" SCNu32, &number) == 1) return number; return 0; } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的一个字段. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 新串 */ char *iptux_get_section_string(const char *msg, char ch, uint8_t times) { const char *pptr, *ptr; char *string; size_t len; if (!(pptr = iptux_skip_section(msg, ch, times))) return NULL; ptr = strchr(pptr, ch); if ((len = ptr ? ptr - pptr : strlen(pptr)) == 0) return NULL; string = g_strndup(pptr, len); return string; } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的一个文件名. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 新串 * * @note 文件名特殊格式请参考IPMsg协议 * @note (msg)串会被修改 */ char *ipmsg_get_filename(const char *msg, char ch, uint8_t times) { static uint32_t serial = 1; char filename[256]; //文件最大长度为255 const char *ptr; size_t len; if ((ptr = iptux_skip_section(msg, ch, times))) { len = 0; while (*ptr != ':' || strncmp(ptr, "::", 2) == 0) { if (len < 255) { //防止缓冲区溢出 filename[len] = *ptr; len++; } if (*ptr == ':') { //抹除分割符 memcpy((void *)ptr, "xx", 2); ptr++; } ptr++; } filename[len] = '\0'; } else snprintf(filename, 256, "%" PRIu32 "_file", serial++); return g_strdup(filename); } /** * 读取以(msg)为起始点,跳跃(times)次(ch)字符后的完整串. * @param msg 串起始点 * @param ch 分割字符 * @param times 跳跃次数 * @return 新串 */ char *ipmsg_get_attach(const char *msg, char ch, uint8_t times) { const char *ptr; if (!(ptr = iptux_skip_section(msg, ch, times))) return NULL; return g_strdup(ptr); } /** * 从文件路径中分离出文件名,并转化为(IPMsg)格式的文件名. * @param pathname 文件路径 * @return 文件名 * * @note 文件名特殊格式请参考IPMsg协议 */ char *ipmsg_get_filename_pal(const char *pathname) { char filename[512]; //文件最大长度为255 const char *ptr; size_t len; ptr = strrchr(pathname, '/'); ptr = ptr ? ptr + 1 : pathname; len = 0; while (*ptr && len < 510) { if (*ptr == ':') { memcpy(filename + len, "::", 2); len += 2; } else { filename[len] = *ptr; len++; } ptr++; } filename[len] = '\0'; return g_strdup(filename); } /** * 从文件路径中分离出文件名以及路径. * @param pathname 文件路径 * @retval path 路径由此返回 * @return 文件名 * * @note 路径可能为NULL */ char *ipmsg_get_filename_me(const char *pathname, char **path) { const char *ptr; char *file; ptr = strrchr(pathname, '/'); if (ptr && ptr != pathname) { file = g_strdup(ptr + 1); if (path) *path = g_strndup(pathname, ptr - pathname); } else { file = g_strdup(pathname); if (path) *path = NULL; } return file; } /** * 从文件名中移除后缀. * @param filename 文件名 * @return 文件 * */ char *iptux_erase_filename_suffix(const char *filename) { const char *ptr; char *file; ptr = strrchr(filename, '.'); if (ptr && ptr != filename) file = g_strndup(filename, ptr - filename); else file = g_strdup(filename); return file; } /** * 从给定的文件路径和文件名返回全文件名. * @param path 文件路径 * @param name 文件名 * @return 带路径的文件名 * */ char *ipmsg_get_pathname_full(const char *path, const char *name) { char filename[MAX_PATHLEN]; strcpy(filename, path); strcat(filename, "/"); strcat(filename, name); return g_strdup(filename); } void FLAG_SET(uint8_t &num, int bit) { ((num) |= (1 << (bit))); } void FLAG_SET(uint8_t &num, int bit, bool value) { if (value) { ((num) |= (1 << (bit))); } else { ((num) &= (~(1 << (bit)))); } } bool ValidateDragData(GtkSelectionData *data, GdkDragContext *context, guint time) { if (gtk_selection_data_get_length(data) <= 0 || gtk_selection_data_get_format(data) != 8) { gtk_drag_finish(context, FALSE, FALSE, time); return false; } return true; } } // namespace iptuxiptux-0.7.4/src/iptux/utils.h000066400000000000000000000056331323207530100161470ustar00rootroot00000000000000// // C++ Interface: utils // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_UTILS_H #define IPTUX_UTILS_H #include #include "iptux/mess.h" namespace iptux { #define difftimeval(val2, val1) \ ((((val2).tv_sec - (val1).tv_sec) * 1000000 + (val2).tv_usec - \ (val1).tv_usec) / \ 1000000.0f) #define percent(num1, num2) (100.0f * (num1) / (num2)) #define FLAG_ISSET(num, bit) ((num) & (1 << (bit))) void FLAG_SET(uint8_t &num, int bit); void FLAG_SET(uint8_t &num, int bit, bool value); #define FLAG_CLR(num, bit) ((num) &= (~(1 << (bit)))) #define URL_REGEX \ "(http|ftp|https|sftp):\\/\\/[\\w\\-_]+(\\.[\\w\\-_]+)+" \ "([\\w\\-\\.,@?^=%&:/~\\+#]*[\\w\\-\\@?^=%&/~\\+#])?" #define NO_OPERATION_C \ while (0) \ ; typedef void *(*ThreadFunc)(void *); void ipv4_order(in_addr_t *ip1, in_addr_t *ip2); char *iptux_string_validate(const char *string, const std::string &codeset, char **encode); char *iptux_string_validate_copy(const char *string, const char *codeset, char **encode); char *convert_encode(const char *string, const char *tocode, const char *fromcode); char *convert_encode_copy(const char *string, const char *tocode, const char *fromcode); void get_file_system_info(const char *path, int64_t *avail, int64_t *total); char *iptux_string_getline(const char *str); char *assert_filename_inexist(const char *path); char *getformattime(gboolean date, const char *format, ...); gboolean giter_compare_foreach(gunichar src, gunichar dst); char *numeric_to_size(int64_t numeric); char *numeric_to_rate(uint32_t numeric); char *numeric_to_time(uint32_t numeric); /* 以下函数调用的(ch)参数字符不应为('\0') */ const char *iptux_skip_string(const char *string, size_t size, uint8_t times); const char *iptux_skip_section(const char *string, char ch, uint8_t times); int64_t iptux_get_hex64_number(const char *msg, char ch, uint8_t times); uint32_t iptux_get_hex_number(const char *msg, char ch, uint8_t times); uint32_t iptux_get_dec_number(const char *msg, char ch, uint8_t times); char *iptux_get_section_string(const char *msg, char ch, uint8_t times); char *ipmsg_get_filename(const char *msg, char ch, uint8_t times); char *ipmsg_get_attach(const char *msg, char ch, uint8_t times); char *ipmsg_get_filename_pal(const char *pathname); char *ipmsg_get_filename_me(const char *pathname, char **path); char *iptux_erase_filename_suffix(const char *filename); char *ipmsg_get_pathname_full(const char *path, const char *name); bool ValidateDragData(GtkSelectionData *data, GdkDragContext *context, guint time); } // namespace iptux #endif iptux-0.7.4/src/iptux/wrapper.cpp000066400000000000000000000116651323207530100170240ustar00rootroot00000000000000// // C++ Implementation: wrapper // // Description: // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #include "wrapper.h" #include #include #include #include #include "iptux/deplib.h" using namespace std; namespace iptux { /** * 写出数据. * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区有效数据长度 * @return 成功写出的数据长度 */ ssize_t xwrite(int fd, const void *buf, size_t count) { size_t offset; ssize_t size; size = -1; offset = 0; while ((offset != count) && (size != 0)) { if ((size = write(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) continue; return -1; } offset += size; } return offset; } /** * 读取数据. * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区长度 * @return 成功读取的数据长度 */ ssize_t xread(int fd, void *buf, size_t count) { size_t offset; ssize_t size; size = -1; offset = 0; while ((offset != count) && (size != 0)) { if ((size = read(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) continue; return -1; } offset += size; } return offset; } /** * 读取ipmsg消息前缀. * Ver(1):PacketNo:SenderName:SenderHost:CommandNo:AdditionalSection.\n * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区长度 * @return 成功读取的消息长度,-1表示读取消息出错 */ ssize_t read_ipmsg_prefix(int fd, void *buf, size_t count) { uint number; size_t offset; ssize_t size; size = -1; offset = 0; number = 0; while ((offset != count) && (size != 0)) { if ((size = read(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) continue; return -1; } offset += size; const char *endptr = (const char *)buf + offset; for (const char *curptr = endptr - size; curptr < endptr; ++curptr) { if (*curptr == ':') ++number; } if (number >= 5) break; } return offset; } /** * 读取ipmsg文件请求消息前缀. * packetID:fileID:offset.\n * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区长度 * @param offset 缓冲区无效数据偏移量 * @return 成功读取的消息长度,-1表示读取消息出错 */ ssize_t read_ipmsg_filedata(int fd, void *buf, size_t count, size_t offset) { const char *curptr; uint number; ssize_t size; size = -1; number = 0; curptr = (const char *)buf; while ((offset != count) && (size != 0)) { const char *endptr = (const char *)buf + offset; for (; curptr < endptr; ++curptr) { if (*curptr == ':') ++number; } if (number > 2 || (number == 2 && *(curptr - 1) != ':')) break; if ((size = read(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) continue; return -1; } offset += size; } return offset; } /** * 读取ipmsg目录请求消息前缀. * packetID:fileID.\n * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区长度 * @param offset 缓冲区无效数据偏移量 * @return 成功读取的消息长度,-1表示读取消息出错 */ ssize_t read_ipmsg_dirfiles(int fd, void *buf, size_t count, size_t offset) { const char *curptr; uint number; ssize_t size; size = -1; number = 0; curptr = (const char *)buf; while ((offset != count) && (size != 0)) { const char *endptr = (const char *)buf + offset; for (; curptr < endptr; ++curptr) { if (*curptr == ':') ++number; } if (number > 1 || (number == 1 && *(curptr - 1) != ':')) break; if ((size = read(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) continue; return -1; } offset += size; } return offset; } /** * 读取ipmsg文件头信息. * 本函数的退出条件为: \n * 1.缓冲区内必须要有数据; \n * 2.文件头长度必须能够被获得; \n * 3.文件头长度必须小于或等于缓冲区内已有数据长度; \n * 4.读取数据出错(晕,这还值得怀疑吗?). \n * @param fd 文件描述符 * @param buf 缓冲区 * @param count 缓冲区长度 * @param offset 缓冲区无效数据偏移量 * @return 成功读取的信息长度 */ ssize_t read_ipmsg_fileinfo(int fd, void *buf, size_t count, size_t offset) { ssize_t size; uint32_t headsize; if (offset < count) //注意不要写到缓冲区外了 ((char *)buf)[offset] = '\0'; while (!offset || !strchr((char *)buf, ':') || sscanf((char *)buf, "%" SCNx32, &headsize) != 1 || headsize > offset) { mark: if ((size = read(fd, (char *)buf + offset, count - offset)) == -1) { if (errno == EINTR) goto mark; return -1; } else if (size == 0) return -1; if ((offset += size) == count) break; ((char *)buf)[offset] = '\0'; } return offset; } } // namespace iptux iptux-0.7.4/src/iptux/wrapper.h000066400000000000000000000013331323207530100164600ustar00rootroot00000000000000// // C++ Interface: wrapper // // Description:打包函数,使某些函数更加好用 // // // Author: Jally , (C) 2008 // // Copyright: See COPYING file that comes with this distribution // // #ifndef IPTUX_WRAPPER_H #define IPTUX_WRAPPER_H #include namespace iptux { ssize_t xwrite(int fd, const void *buf, size_t count); ssize_t xread(int fd, void *buf, size_t count); ssize_t read_ipmsg_prefix(int fd, void *buf, size_t count); ssize_t read_ipmsg_filedata(int fd, void *buf, size_t count, size_t offset); ssize_t read_ipmsg_dirfiles(int fd, void *buf, size_t count, size_t offset); ssize_t read_ipmsg_fileinfo(int fd, void *buf, size_t count, size_t offset); } // namespace iptux #endif iptux-0.7.4/src/main/000077500000000000000000000000001323207530100144025ustar00rootroot00000000000000iptux-0.7.4/src/main/CMakeLists.txt000066400000000000000000000012161323207530100171420ustar00rootroot00000000000000pkg_check_modules (IPTUX REQUIRED glib-2.0>=2.32.0 gthread-2.0>=2.14.0 gtk+-2.0>=2.16.0 jsoncpp>=1.0) include_directories("${PROJECT_SOURCE_DIR}/src" "${PROJECT_BINARY_DIR}/src" "${IPTUX_INCLUDE_DIRS}") link_libraries("${IPTUX_LIBRARIES}") link_libraries("${Intl_LIBRARIES}") if(GST_FOUND) include_directories("${GST_INCLUDE_DIRS}") link_libraries("${GST_LIBRARIES}") endif(GST_FOUND) add_executable (iptuxbin iptux.cpp ) set_target_properties(iptuxbin PROPERTIES OUTPUT_NAME iptux) set(THREADS_PREFER_PTHREAD_FLAG ON) find_package(Threads REQUIRED) target_link_libraries(iptuxbin iptux Threads::Threads) install (TARGETS iptuxbin DESTINATION bin) iptux-0.7.4/src/main/iptux.cpp000066400000000000000000000130051323207530100162560ustar00rootroot00000000000000/*************************************************************************** * Copyright (C) 2008 by Jally * * jallyx@163.com * * * * 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 2 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, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include #include #include #include "iptux/CoreThread.h" #include "iptux/LogSystem.h" #include "iptux/MainWindow.h" #include "iptux/ProgramData.h" #include "iptux/SoundSystem.h" #include "iptux/StatusIcon.h" #include "iptux/config.h" #include "iptux/deplib.h" #include "iptux/ipmsg.h" #include "iptux/output.h" #include "iptux/support.h" using namespace std; using namespace iptux; namespace iptux { ProgramData* g_progdt; CoreThread* g_cthrd; MainWindow* g_mwin; SoundSystem* g_sndsys; LogSystem* g_lgsys; } // namespace iptux string getConfigPath() { const char* res1 = g_build_path("/", g_getenv("HOME"), ".iptux", "config.json", NULL); string res2(res1); g_free(gpointer(res1)); return res2; } static gboolean version = FALSE; static gchar* configFilename = nullptr; static gchar* log = nullptr; static GLogLevelFlags logLevel = G_LOG_LEVEL_WARNING; static GOptionEntry entries[] = { {"version", 'v', 0, G_OPTION_ARG_NONE, &version, "Output version information and exit", NULL}, {"config", 'c', 0, G_OPTION_ARG_FILENAME, &configFilename, "Specify config path", "CONFIG_PATH"}, {"log", 'l', 0, G_OPTION_ARG_STRING, &log, "Specify log level: DEBUG, INFO, WARN, default is WARN", "LEVEL"}, {NULL}}; static string nowAsString() { time_t rawtime; struct tm* timeinfo; char buffer[80]; time(&rawtime); timeinfo = localtime(&rawtime); strftime(buffer, sizeof(buffer), "%Y-%m-%d %H:%M:%S", timeinfo); return buffer; } static const char* logLevelAsString(GLogLevelFlags logLevel) { switch (logLevel) { case G_LOG_LEVEL_DEBUG: return "DEBUG"; case G_LOG_LEVEL_INFO: return "INFO "; case G_LOG_LEVEL_MESSAGE: return "MESSA"; case G_LOG_LEVEL_WARNING: return "WARN "; case G_LOG_LEVEL_ERROR: return "ERROR"; default: return "UNKNO"; } } static void logHandler(const gchar* log_domain, GLogLevelFlags log_level, const gchar* message, gpointer user_data) { if (log_level > logLevel) { return; } fprintf(stderr, "[%s][%s][%s]%s\n", nowAsString().c_str(), log_domain, logLevelAsString(log_level), message); } static void dealLog(const IptuxConfig& config) { string logStr = "WARN"; if (!config.GetString("log_level").empty()) { logStr = config.GetString("log_level"); } if (log != nullptr) { logStr = log; } g_log_set_handler("iptux", GLogLevelFlags(G_LOG_LEVEL_MASK | G_LOG_FLAG_FATAL | G_LOG_FLAG_RECURSION), logHandler, NULL); if (logStr == "DEBUG") { logLevel = G_LOG_LEVEL_DEBUG; } else if (logStr == "INFO") { logLevel = G_LOG_LEVEL_INFO; } else if (logStr == "WARN") { logLevel = G_LOG_LEVEL_WARNING; } else { LOG_ERROR("unknown log level: %s", log); } } int main(int argc, char* argv[]) { setlocale(LC_ALL, ""); bindtextdomain(GETTEXT_PACKAGE, __LOCALE_PATH); bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8"); textdomain(GETTEXT_PACKAGE); GError* error = NULL; GOptionContext* context; context = g_option_context_new(_("- A software for sharing in LAN")); g_option_context_add_main_entries(context, entries, GETTEXT_PACKAGE); g_option_context_add_group(context, gtk_get_option_group(TRUE)); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print(_("option parsing failed: %s\n"), error->message); exit(1); } if (version) { printf("iptux: " VERSION "\n"); exit(0); } string configPath = configFilename ? configFilename : getConfigPath(); IptuxConfig config(configPath); dealLog(config); ProgramData progdt(config); MainWindow mwin(config, progdt); CoreThread cthrd(config); StatusIcon sicon(config, mwin); LogSystem lgsys; SoundSystem sndsys; g_progdt = &progdt; g_cthrd = &cthrd; g_mwin = &mwin; g_sndsys = &sndsys; g_lgsys = &lgsys; mwin.SetStatusIcon(&sicon); gdk_threads_init(); gdk_threads_enter(); gtk_init(&argc, &argv); int port = config.GetInt("port", IPTUX_DEFAULT_PORT); iptux_init(port); sicon.CreateStatusIcon(); mwin.CreateWindow(); cthrd.CoreThreadEntry(); gtk_main(); gdk_threads_leave(); return 0; }