From d796c9dd933ab96ec83b9a634feedd5d32e1ba3f Mon Sep 17 00:00:00 2001 From: Timothy Pearson Date: Tue, 8 Nov 2011 12:31:36 -0600 Subject: Test conversion to TQt3 from Qt3 8c6fc1f8e35fd264dd01c582ca5e7549b32ab731 --- tools/linguist/LICENSE.GPL | 280 +++ tools/linguist/book/images/doneandnext.png | Bin 0 -> 445 bytes tools/linguist/book/images/editcopy.png | Bin 0 -> 587 bytes tools/linguist/book/images/editcut.png | Bin 0 -> 480 bytes tools/linguist/book/images/editfind.png | Bin 0 -> 776 bytes tools/linguist/book/images/editpaste.png | Bin 0 -> 664 bytes tools/linguist/book/images/editredo.png | Bin 0 -> 362 bytes tools/linguist/book/images/editundo.png | Bin 0 -> 353 bytes tools/linguist/book/images/fileopen.png | Bin 0 -> 523 bytes tools/linguist/book/images/fileprint.png | Bin 0 -> 767 bytes tools/linguist/book/images/filesave.png | Bin 0 -> 510 bytes tools/linguist/book/images/finddialog.png | Bin 0 -> 3165 bytes tools/linguist/book/images/linguist.png | Bin 0 -> 22819 bytes tools/linguist/book/images/menubar.png | Bin 0 -> 511 bytes tools/linguist/book/images/next.png | Bin 0 -> 418 bytes tools/linguist/book/images/nextunfinished.png | Bin 0 -> 456 bytes tools/linguist/book/images/phrasebookdialog.png | Bin 0 -> 4857 bytes tools/linguist/book/images/phrasebookopen.png | Bin 0 -> 883 bytes tools/linguist/book/images/prev.png | Bin 0 -> 412 bytes tools/linguist/book/images/prevunfinished.png | Bin 0 -> 449 bytes tools/linguist/book/images/toolbar.png | Bin 0 -> 5397 bytes tools/linguist/book/images/tt1_en.png | Bin 0 -> 872 bytes tools/linguist/book/images/tt1_la.png | Bin 0 -> 894 bytes tools/linguist/book/images/tt2_en.png | Bin 0 -> 1615 bytes tools/linguist/book/images/tt2_fr.png | Bin 0 -> 1854 bytes tools/linguist/book/images/tt2_nl.png | Bin 0 -> 1881 bytes tools/linguist/book/images/tt3_10_en.png | Bin 0 -> 2286 bytes tools/linguist/book/images/tt3_10_pt_bad.png | Bin 0 -> 2411 bytes tools/linguist/book/images/tt3_10_pt_good.png | Bin 0 -> 2485 bytes tools/linguist/book/images/tt3_11_about_pt.png | Bin 0 -> 2720 bytes tools/linguist/book/images/tt3_11_en.png | Bin 0 -> 2368 bytes tools/linguist/book/images/tt3_11_pt.png | Bin 0 -> 2537 bytes .../linguist/book/images/validateaccelerators.png | Bin 0 -> 387 bytes tools/linguist/book/images/validatephrases.png | Bin 0 -> 293 bytes tools/linguist/book/images/validatepunctuation.png | Bin 0 -> 373 bytes tools/linguist/book/linguist-manager.leaf | 138 ++ tools/linguist/book/linguist-manual.book | 90 + tools/linguist/book/linguist-programmer.leaf | 1145 +++++++++++ tools/linguist/book/linguist-translator.leaf | 582 ++++++ tools/linguist/linguist.pro | 11 + tools/linguist/linguist/about.ui | 223 +++ tools/linguist/linguist/finddialog.cpp | 183 ++ tools/linguist/linguist/finddialog.h | 68 + tools/linguist/linguist/images/accelerator.png | Bin 0 -> 782 bytes tools/linguist/linguist/images/appicon.png | Bin 0 -> 1936 bytes tools/linguist/linguist/images/book.png | Bin 0 -> 825 bytes tools/linguist/linguist/images/d_accelerator.png | Bin 0 -> 487 bytes tools/linguist/linguist/images/d_book.png | Bin 0 -> 557 bytes tools/linguist/linguist/images/d_doneandnext.png | Bin 0 -> 457 bytes tools/linguist/linguist/images/d_editcopy.png | Bin 0 -> 526 bytes tools/linguist/linguist/images/d_editcut.png | Bin 0 -> 800 bytes tools/linguist/linguist/images/d_editpaste.png | Bin 0 -> 610 bytes tools/linguist/linguist/images/d_fileopen.png | Bin 0 -> 406 bytes tools/linguist/linguist/images/d_filesave.png | Bin 0 -> 267 bytes tools/linguist/linguist/images/d_next.png | Bin 0 -> 446 bytes .../linguist/linguist/images/d_nextunfinished.png | Bin 0 -> 522 bytes tools/linguist/linguist/images/d_phrase.png | Bin 0 -> 290 bytes tools/linguist/linguist/images/d_prev.png | Bin 0 -> 425 bytes .../linguist/linguist/images/d_prevunfinished.png | Bin 0 -> 542 bytes tools/linguist/linguist/images/d_print.png | Bin 0 -> 595 bytes tools/linguist/linguist/images/d_punctuation.png | Bin 0 -> 356 bytes tools/linguist/linguist/images/d_redo.png | Bin 0 -> 465 bytes .../linguist/linguist/images/d_s_check_danger.png | Bin 0 -> 270 bytes tools/linguist/linguist/images/d_s_check_obs.png | Bin 0 -> 220 bytes tools/linguist/linguist/images/d_s_check_off.png | Bin 0 -> 348 bytes tools/linguist/linguist/images/d_s_check_on.png | Bin 0 -> 220 bytes tools/linguist/linguist/images/d_searchfind.png | Bin 0 -> 501 bytes tools/linguist/linguist/images/d_undo.png | Bin 0 -> 471 bytes tools/linguist/linguist/images/doneandnext.png | Bin 0 -> 532 bytes tools/linguist/linguist/images/editcopy.png | Bin 0 -> 491 bytes tools/linguist/linguist/images/editcut.png | Bin 0 -> 649 bytes tools/linguist/linguist/images/editpaste.png | Bin 0 -> 864 bytes tools/linguist/linguist/images/fileopen.png | Bin 0 -> 681 bytes tools/linguist/linguist/images/filesave.png | Bin 0 -> 328 bytes tools/linguist/linguist/images/next.png | Bin 0 -> 541 bytes tools/linguist/linguist/images/nextunfinished.png | Bin 0 -> 649 bytes tools/linguist/linguist/images/pagecurl.png | Bin 0 -> 1247 bytes tools/linguist/linguist/images/phrase.png | Bin 0 -> 366 bytes tools/linguist/linguist/images/prev.png | Bin 0 -> 542 bytes tools/linguist/linguist/images/prevunfinished.png | Bin 0 -> 725 bytes tools/linguist/linguist/images/print.png | Bin 0 -> 766 bytes tools/linguist/linguist/images/punctuation.png | Bin 0 -> 502 bytes tools/linguist/linguist/images/redo.png | Bin 0 -> 592 bytes tools/linguist/linguist/images/s_check_danger.png | Bin 0 -> 326 bytes tools/linguist/linguist/images/s_check_obs.png | Bin 0 -> 245 bytes tools/linguist/linguist/images/s_check_off.png | Bin 0 -> 439 bytes tools/linguist/linguist/images/s_check_on.png | Bin 0 -> 235 bytes tools/linguist/linguist/images/searchfind.png | Bin 0 -> 843 bytes tools/linguist/linguist/images/splash.png | Bin 0 -> 31939 bytes tools/linguist/linguist/images/undo.png | Bin 0 -> 572 bytes tools/linguist/linguist/images/whatsthis.xpm | 24 + tools/linguist/linguist/linguist.icns | Bin 0 -> 47620 bytes tools/linguist/linguist/linguist.ico | Bin 0 -> 10134 bytes tools/linguist/linguist/linguist.pro | 109 ++ tools/linguist/linguist/linguist.rc | 1 + tools/linguist/linguist/linguist_de.ts | 993 ++++++++++ tools/linguist/linguist/linguist_fr.ts | 993 ++++++++++ tools/linguist/linguist/listviews.cpp | 350 ++++ tools/linguist/linguist/listviews.h | 135 ++ tools/linguist/linguist/main.cpp | 89 + tools/linguist/linguist/msgedit.cpp | 834 ++++++++ tools/linguist/linguist/msgedit.h | 244 +++ tools/linguist/linguist/phrase.cpp | 189 ++ tools/linguist/linguist/phrase.h | 74 + tools/linguist/linguist/phrasebookbox.cpp | 244 +++ tools/linguist/linguist/phrasebookbox.h | 84 + tools/linguist/linguist/phraselv.cpp | 171 ++ tools/linguist/linguist/phraselv.h | 83 + tools/linguist/linguist/printout.cpp | 182 ++ tools/linguist/linguist/printout.h | 126 ++ tools/linguist/linguist/simtexth.cpp | 239 +++ tools/linguist/linguist/simtexth.h | 64 + tools/linguist/linguist/statistics.ui | 259 +++ tools/linguist/linguist/statistics.ui.h | 53 + tools/linguist/linguist/trwindow.cpp | 2071 ++++++++++++++++++++ tools/linguist/linguist/trwindow.h | 237 +++ tools/linguist/lrelease/lrelease.pro | 17 + tools/linguist/lrelease/main.cpp | 203 ++ tools/linguist/lupdate/fetchtr.cpp | 824 ++++++++ tools/linguist/lupdate/lupdate.pro | 21 + tools/linguist/lupdate/main.cpp | 241 +++ tools/linguist/lupdate/merge.cpp | 129 ++ tools/linguist/lupdate/numberh.cpp | 248 +++ tools/linguist/lupdate/sametexth.cpp | 97 + tools/linguist/phrasebooks/danish.qph | 1018 ++++++++++ tools/linguist/phrasebooks/dutch.qph | 1044 ++++++++++ tools/linguist/phrasebooks/finnish.qph | 1033 ++++++++++ tools/linguist/phrasebooks/french.qph | 1104 +++++++++++ tools/linguist/phrasebooks/german.qph | 1075 ++++++++++ tools/linguist/phrasebooks/italian.qph | 1105 +++++++++++ tools/linguist/phrasebooks/norwegian.qph | 1004 ++++++++++ tools/linguist/phrasebooks/russian.qph | 982 ++++++++++ tools/linguist/phrasebooks/spanish.qph | 1086 ++++++++++ tools/linguist/phrasebooks/swedish.qph | 1010 ++++++++++ tools/linguist/qdoc.conf | 15 + tools/linguist/qm2ts/main.cpp | 128 ++ tools/linguist/qm2ts/qm2ts.1 | 55 + tools/linguist/qm2ts/qm2ts.pro | 15 + tools/linguist/shared/metatranslator.cpp | 601 ++++++ tools/linguist/shared/metatranslator.h | 120 ++ tools/linguist/shared/proparser.cpp | 217 ++ tools/linguist/shared/proparser.h | 42 + tools/linguist/tutorial/tt1/main.cpp | 25 + tools/linguist/tutorial/tt1/tt1.pro | 4 + tools/linguist/tutorial/tt2/arrowpad.cpp | 31 + tools/linguist/tutorial/tt2/arrowpad.h | 22 + tools/linguist/tutorial/tt2/main.cpp | 26 + tools/linguist/tutorial/tt2/mainwindow.cpp | 26 + tools/linguist/tutorial/tt2/mainwindow.h | 19 + tools/linguist/tutorial/tt2/tt2.pro | 9 + tools/linguist/tutorial/tt3/main.cpp | 26 + tools/linguist/tutorial/tt3/mainwindow.cpp | 47 + tools/linguist/tutorial/tt3/mainwindow.h | 23 + tools/linguist/tutorial/tt3/printpanel.cpp | 37 + tools/linguist/tutorial/tt3/printpanel.h | 19 + tools/linguist/tutorial/tt3/tt3.pro | 8 + tools/linguist/tutorial/tt3/tt3_pt.ts | 65 + 157 files changed, 24389 insertions(+) create mode 100644 tools/linguist/LICENSE.GPL create mode 100644 tools/linguist/book/images/doneandnext.png create mode 100644 tools/linguist/book/images/editcopy.png create mode 100644 tools/linguist/book/images/editcut.png create mode 100644 tools/linguist/book/images/editfind.png create mode 100644 tools/linguist/book/images/editpaste.png create mode 100644 tools/linguist/book/images/editredo.png create mode 100644 tools/linguist/book/images/editundo.png create mode 100644 tools/linguist/book/images/fileopen.png create mode 100644 tools/linguist/book/images/fileprint.png create mode 100644 tools/linguist/book/images/filesave.png create mode 100644 tools/linguist/book/images/finddialog.png create mode 100644 tools/linguist/book/images/linguist.png create mode 100644 tools/linguist/book/images/menubar.png create mode 100644 tools/linguist/book/images/next.png create mode 100644 tools/linguist/book/images/nextunfinished.png create mode 100644 tools/linguist/book/images/phrasebookdialog.png create mode 100644 tools/linguist/book/images/phrasebookopen.png create mode 100644 tools/linguist/book/images/prev.png create mode 100644 tools/linguist/book/images/prevunfinished.png create mode 100644 tools/linguist/book/images/toolbar.png create mode 100644 tools/linguist/book/images/tt1_en.png create mode 100644 tools/linguist/book/images/tt1_la.png create mode 100644 tools/linguist/book/images/tt2_en.png create mode 100644 tools/linguist/book/images/tt2_fr.png create mode 100644 tools/linguist/book/images/tt2_nl.png create mode 100644 tools/linguist/book/images/tt3_10_en.png create mode 100644 tools/linguist/book/images/tt3_10_pt_bad.png create mode 100644 tools/linguist/book/images/tt3_10_pt_good.png create mode 100644 tools/linguist/book/images/tt3_11_about_pt.png create mode 100644 tools/linguist/book/images/tt3_11_en.png create mode 100644 tools/linguist/book/images/tt3_11_pt.png create mode 100644 tools/linguist/book/images/validateaccelerators.png create mode 100644 tools/linguist/book/images/validatephrases.png create mode 100644 tools/linguist/book/images/validatepunctuation.png create mode 100644 tools/linguist/book/linguist-manager.leaf create mode 100644 tools/linguist/book/linguist-manual.book create mode 100644 tools/linguist/book/linguist-programmer.leaf create mode 100644 tools/linguist/book/linguist-translator.leaf create mode 100644 tools/linguist/linguist.pro create mode 100644 tools/linguist/linguist/about.ui create mode 100644 tools/linguist/linguist/finddialog.cpp create mode 100644 tools/linguist/linguist/finddialog.h create mode 100644 tools/linguist/linguist/images/accelerator.png create mode 100644 tools/linguist/linguist/images/appicon.png create mode 100644 tools/linguist/linguist/images/book.png create mode 100644 tools/linguist/linguist/images/d_accelerator.png create mode 100644 tools/linguist/linguist/images/d_book.png create mode 100644 tools/linguist/linguist/images/d_doneandnext.png create mode 100644 tools/linguist/linguist/images/d_editcopy.png create mode 100644 tools/linguist/linguist/images/d_editcut.png create mode 100644 tools/linguist/linguist/images/d_editpaste.png create mode 100644 tools/linguist/linguist/images/d_fileopen.png create mode 100644 tools/linguist/linguist/images/d_filesave.png create mode 100644 tools/linguist/linguist/images/d_next.png create mode 100644 tools/linguist/linguist/images/d_nextunfinished.png create mode 100644 tools/linguist/linguist/images/d_phrase.png create mode 100644 tools/linguist/linguist/images/d_prev.png create mode 100644 tools/linguist/linguist/images/d_prevunfinished.png create mode 100644 tools/linguist/linguist/images/d_print.png create mode 100644 tools/linguist/linguist/images/d_punctuation.png create mode 100644 tools/linguist/linguist/images/d_redo.png create mode 100644 tools/linguist/linguist/images/d_s_check_danger.png create mode 100644 tools/linguist/linguist/images/d_s_check_obs.png create mode 100644 tools/linguist/linguist/images/d_s_check_off.png create mode 100644 tools/linguist/linguist/images/d_s_check_on.png create mode 100644 tools/linguist/linguist/images/d_searchfind.png create mode 100644 tools/linguist/linguist/images/d_undo.png create mode 100644 tools/linguist/linguist/images/doneandnext.png create mode 100644 tools/linguist/linguist/images/editcopy.png create mode 100644 tools/linguist/linguist/images/editcut.png create mode 100644 tools/linguist/linguist/images/editpaste.png create mode 100644 tools/linguist/linguist/images/fileopen.png create mode 100644 tools/linguist/linguist/images/filesave.png create mode 100644 tools/linguist/linguist/images/next.png create mode 100644 tools/linguist/linguist/images/nextunfinished.png create mode 100644 tools/linguist/linguist/images/pagecurl.png create mode 100644 tools/linguist/linguist/images/phrase.png create mode 100644 tools/linguist/linguist/images/prev.png create mode 100644 tools/linguist/linguist/images/prevunfinished.png create mode 100644 tools/linguist/linguist/images/print.png create mode 100644 tools/linguist/linguist/images/punctuation.png create mode 100644 tools/linguist/linguist/images/redo.png create mode 100644 tools/linguist/linguist/images/s_check_danger.png create mode 100644 tools/linguist/linguist/images/s_check_obs.png create mode 100644 tools/linguist/linguist/images/s_check_off.png create mode 100644 tools/linguist/linguist/images/s_check_on.png create mode 100644 tools/linguist/linguist/images/searchfind.png create mode 100644 tools/linguist/linguist/images/splash.png create mode 100644 tools/linguist/linguist/images/undo.png create mode 100644 tools/linguist/linguist/images/whatsthis.xpm create mode 100644 tools/linguist/linguist/linguist.icns create mode 100644 tools/linguist/linguist/linguist.ico create mode 100644 tools/linguist/linguist/linguist.pro create mode 100644 tools/linguist/linguist/linguist.rc create mode 100644 tools/linguist/linguist/linguist_de.ts create mode 100644 tools/linguist/linguist/linguist_fr.ts create mode 100644 tools/linguist/linguist/listviews.cpp create mode 100644 tools/linguist/linguist/listviews.h create mode 100644 tools/linguist/linguist/main.cpp create mode 100644 tools/linguist/linguist/msgedit.cpp create mode 100644 tools/linguist/linguist/msgedit.h create mode 100644 tools/linguist/linguist/phrase.cpp create mode 100644 tools/linguist/linguist/phrase.h create mode 100644 tools/linguist/linguist/phrasebookbox.cpp create mode 100644 tools/linguist/linguist/phrasebookbox.h create mode 100644 tools/linguist/linguist/phraselv.cpp create mode 100644 tools/linguist/linguist/phraselv.h create mode 100644 tools/linguist/linguist/printout.cpp create mode 100644 tools/linguist/linguist/printout.h create mode 100644 tools/linguist/linguist/simtexth.cpp create mode 100644 tools/linguist/linguist/simtexth.h create mode 100644 tools/linguist/linguist/statistics.ui create mode 100644 tools/linguist/linguist/statistics.ui.h create mode 100644 tools/linguist/linguist/trwindow.cpp create mode 100644 tools/linguist/linguist/trwindow.h create mode 100644 tools/linguist/lrelease/lrelease.pro create mode 100644 tools/linguist/lrelease/main.cpp create mode 100644 tools/linguist/lupdate/fetchtr.cpp create mode 100644 tools/linguist/lupdate/lupdate.pro create mode 100644 tools/linguist/lupdate/main.cpp create mode 100644 tools/linguist/lupdate/merge.cpp create mode 100644 tools/linguist/lupdate/numberh.cpp create mode 100644 tools/linguist/lupdate/sametexth.cpp create mode 100644 tools/linguist/phrasebooks/danish.qph create mode 100644 tools/linguist/phrasebooks/dutch.qph create mode 100644 tools/linguist/phrasebooks/finnish.qph create mode 100644 tools/linguist/phrasebooks/french.qph create mode 100644 tools/linguist/phrasebooks/german.qph create mode 100644 tools/linguist/phrasebooks/italian.qph create mode 100644 tools/linguist/phrasebooks/norwegian.qph create mode 100644 tools/linguist/phrasebooks/russian.qph create mode 100644 tools/linguist/phrasebooks/spanish.qph create mode 100644 tools/linguist/phrasebooks/swedish.qph create mode 100644 tools/linguist/qdoc.conf create mode 100644 tools/linguist/qm2ts/main.cpp create mode 100644 tools/linguist/qm2ts/qm2ts.1 create mode 100644 tools/linguist/qm2ts/qm2ts.pro create mode 100644 tools/linguist/shared/metatranslator.cpp create mode 100644 tools/linguist/shared/metatranslator.h create mode 100644 tools/linguist/shared/proparser.cpp create mode 100644 tools/linguist/shared/proparser.h create mode 100644 tools/linguist/tutorial/tt1/main.cpp create mode 100644 tools/linguist/tutorial/tt1/tt1.pro create mode 100644 tools/linguist/tutorial/tt2/arrowpad.cpp create mode 100644 tools/linguist/tutorial/tt2/arrowpad.h create mode 100644 tools/linguist/tutorial/tt2/main.cpp create mode 100644 tools/linguist/tutorial/tt2/mainwindow.cpp create mode 100644 tools/linguist/tutorial/tt2/mainwindow.h create mode 100644 tools/linguist/tutorial/tt2/tt2.pro create mode 100644 tools/linguist/tutorial/tt3/main.cpp create mode 100644 tools/linguist/tutorial/tt3/mainwindow.cpp create mode 100644 tools/linguist/tutorial/tt3/mainwindow.h create mode 100644 tools/linguist/tutorial/tt3/printpanel.cpp create mode 100644 tools/linguist/tutorial/tt3/printpanel.h create mode 100644 tools/linguist/tutorial/tt3/tt3.pro create mode 100644 tools/linguist/tutorial/tt3/tt3_pt.ts (limited to 'tools/linguist') diff --git a/tools/linguist/LICENSE.GPL b/tools/linguist/LICENSE.GPL new file mode 100644 index 000000000..65cb2ad07 --- /dev/null +++ b/tools/linguist/LICENSE.GPL @@ -0,0 +1,280 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc. + 51 Franklin Steet, 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 Library 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 retquired to print an announcement.) + +These retquirements 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 retquired 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 diff --git a/tools/linguist/book/images/doneandnext.png b/tools/linguist/book/images/doneandnext.png new file mode 100644 index 000000000..47efaec76 Binary files /dev/null and b/tools/linguist/book/images/doneandnext.png differ diff --git a/tools/linguist/book/images/editcopy.png b/tools/linguist/book/images/editcopy.png new file mode 100644 index 000000000..efe8d03ee Binary files /dev/null and b/tools/linguist/book/images/editcopy.png differ diff --git a/tools/linguist/book/images/editcut.png b/tools/linguist/book/images/editcut.png new file mode 100644 index 000000000..146388a29 Binary files /dev/null and b/tools/linguist/book/images/editcut.png differ diff --git a/tools/linguist/book/images/editfind.png b/tools/linguist/book/images/editfind.png new file mode 100644 index 000000000..59c63bf97 Binary files /dev/null and b/tools/linguist/book/images/editfind.png differ diff --git a/tools/linguist/book/images/editpaste.png b/tools/linguist/book/images/editpaste.png new file mode 100644 index 000000000..13f9a0f41 Binary files /dev/null and b/tools/linguist/book/images/editpaste.png differ diff --git a/tools/linguist/book/images/editredo.png b/tools/linguist/book/images/editredo.png new file mode 100644 index 000000000..6a30e2648 Binary files /dev/null and b/tools/linguist/book/images/editredo.png differ diff --git a/tools/linguist/book/images/editundo.png b/tools/linguist/book/images/editundo.png new file mode 100644 index 000000000..38a735758 Binary files /dev/null and b/tools/linguist/book/images/editundo.png differ diff --git a/tools/linguist/book/images/fileopen.png b/tools/linguist/book/images/fileopen.png new file mode 100644 index 000000000..44107d36c Binary files /dev/null and b/tools/linguist/book/images/fileopen.png differ diff --git a/tools/linguist/book/images/fileprint.png b/tools/linguist/book/images/fileprint.png new file mode 100644 index 000000000..2936658f2 Binary files /dev/null and b/tools/linguist/book/images/fileprint.png differ diff --git a/tools/linguist/book/images/filesave.png b/tools/linguist/book/images/filesave.png new file mode 100644 index 000000000..03e10f917 Binary files /dev/null and b/tools/linguist/book/images/filesave.png differ diff --git a/tools/linguist/book/images/finddialog.png b/tools/linguist/book/images/finddialog.png new file mode 100644 index 000000000..c3b0f4332 Binary files /dev/null and b/tools/linguist/book/images/finddialog.png differ diff --git a/tools/linguist/book/images/linguist.png b/tools/linguist/book/images/linguist.png new file mode 100644 index 000000000..519c185ab Binary files /dev/null and b/tools/linguist/book/images/linguist.png differ diff --git a/tools/linguist/book/images/menubar.png b/tools/linguist/book/images/menubar.png new file mode 100644 index 000000000..7ba43c60d Binary files /dev/null and b/tools/linguist/book/images/menubar.png differ diff --git a/tools/linguist/book/images/next.png b/tools/linguist/book/images/next.png new file mode 100644 index 000000000..7434fa21d Binary files /dev/null and b/tools/linguist/book/images/next.png differ diff --git a/tools/linguist/book/images/nextunfinished.png b/tools/linguist/book/images/nextunfinished.png new file mode 100644 index 000000000..618fc947d Binary files /dev/null and b/tools/linguist/book/images/nextunfinished.png differ diff --git a/tools/linguist/book/images/phrasebookdialog.png b/tools/linguist/book/images/phrasebookdialog.png new file mode 100644 index 000000000..d1a323a5a Binary files /dev/null and b/tools/linguist/book/images/phrasebookdialog.png differ diff --git a/tools/linguist/book/images/phrasebookopen.png b/tools/linguist/book/images/phrasebookopen.png new file mode 100644 index 000000000..4f76b7d4c Binary files /dev/null and b/tools/linguist/book/images/phrasebookopen.png differ diff --git a/tools/linguist/book/images/prev.png b/tools/linguist/book/images/prev.png new file mode 100644 index 000000000..f9fbd935d Binary files /dev/null and b/tools/linguist/book/images/prev.png differ diff --git a/tools/linguist/book/images/prevunfinished.png b/tools/linguist/book/images/prevunfinished.png new file mode 100644 index 000000000..25cc1a266 Binary files /dev/null and b/tools/linguist/book/images/prevunfinished.png differ diff --git a/tools/linguist/book/images/toolbar.png b/tools/linguist/book/images/toolbar.png new file mode 100644 index 000000000..5e6021f05 Binary files /dev/null and b/tools/linguist/book/images/toolbar.png differ diff --git a/tools/linguist/book/images/tt1_en.png b/tools/linguist/book/images/tt1_en.png new file mode 100644 index 000000000..66e54e027 Binary files /dev/null and b/tools/linguist/book/images/tt1_en.png differ diff --git a/tools/linguist/book/images/tt1_la.png b/tools/linguist/book/images/tt1_la.png new file mode 100644 index 000000000..a70134908 Binary files /dev/null and b/tools/linguist/book/images/tt1_la.png differ diff --git a/tools/linguist/book/images/tt2_en.png b/tools/linguist/book/images/tt2_en.png new file mode 100644 index 000000000..c71e2010b Binary files /dev/null and b/tools/linguist/book/images/tt2_en.png differ diff --git a/tools/linguist/book/images/tt2_fr.png b/tools/linguist/book/images/tt2_fr.png new file mode 100644 index 000000000..acc25157e Binary files /dev/null and b/tools/linguist/book/images/tt2_fr.png differ diff --git a/tools/linguist/book/images/tt2_nl.png b/tools/linguist/book/images/tt2_nl.png new file mode 100644 index 000000000..4631de21f Binary files /dev/null and b/tools/linguist/book/images/tt2_nl.png differ diff --git a/tools/linguist/book/images/tt3_10_en.png b/tools/linguist/book/images/tt3_10_en.png new file mode 100644 index 000000000..e95bff9e1 Binary files /dev/null and b/tools/linguist/book/images/tt3_10_en.png differ diff --git a/tools/linguist/book/images/tt3_10_pt_bad.png b/tools/linguist/book/images/tt3_10_pt_bad.png new file mode 100644 index 000000000..05cb5f3cf Binary files /dev/null and b/tools/linguist/book/images/tt3_10_pt_bad.png differ diff --git a/tools/linguist/book/images/tt3_10_pt_good.png b/tools/linguist/book/images/tt3_10_pt_good.png new file mode 100644 index 000000000..b0f855f5a Binary files /dev/null and b/tools/linguist/book/images/tt3_10_pt_good.png differ diff --git a/tools/linguist/book/images/tt3_11_about_pt.png b/tools/linguist/book/images/tt3_11_about_pt.png new file mode 100644 index 000000000..446731445 Binary files /dev/null and b/tools/linguist/book/images/tt3_11_about_pt.png differ diff --git a/tools/linguist/book/images/tt3_11_en.png b/tools/linguist/book/images/tt3_11_en.png new file mode 100644 index 000000000..7d98b98cc Binary files /dev/null and b/tools/linguist/book/images/tt3_11_en.png differ diff --git a/tools/linguist/book/images/tt3_11_pt.png b/tools/linguist/book/images/tt3_11_pt.png new file mode 100644 index 000000000..02910cf0d Binary files /dev/null and b/tools/linguist/book/images/tt3_11_pt.png differ diff --git a/tools/linguist/book/images/validateaccelerators.png b/tools/linguist/book/images/validateaccelerators.png new file mode 100644 index 000000000..68201fec8 Binary files /dev/null and b/tools/linguist/book/images/validateaccelerators.png differ diff --git a/tools/linguist/book/images/validatephrases.png b/tools/linguist/book/images/validatephrases.png new file mode 100644 index 000000000..62fe5f281 Binary files /dev/null and b/tools/linguist/book/images/validatephrases.png differ diff --git a/tools/linguist/book/images/validatepunctuation.png b/tools/linguist/book/images/validatepunctuation.png new file mode 100644 index 000000000..8ce2648d9 Binary files /dev/null and b/tools/linguist/book/images/validatepunctuation.png differ diff --git a/tools/linguist/book/linguist-manager.leaf b/tools/linguist/book/linguist-manager.leaf new file mode 100644 index 000000000..9380c4709 --- /dev/null +++ b/tools/linguist/book/linguist-manager.leaf @@ -0,0 +1,138 @@ +\chapter Release Manager + +\index Release Manager + +Two tools are provided for the release manager, \l lupdate and \l +lrelease. These tools depend on \e qmake project files. You don't +have to use \e qmake, though. + +A third tool, \c qm2ts, can be used for converting Qt 2.x message +files to \c .ts files. + +\section1 Qt Project Files + +\index .pro Files +\index Project Files +\index qmake!Project Files + +\l lupdate and \l lrelease depend on information in the application's +\c .pro Qt project file. There must be an entry in the \c TRANSLATIONS +section of the project file for each language that is additional to +the native language. A typical entry looks like this: + +\index TRANSLATIONS!in Project Files + +\quotefile tt2/tt2.pro +\skipto TRANSLATIONS +\printline tt2_fr +\printline tt2_nl + +Using a locale within the translation file name is useful for +determining which language to load at runtime. This is explained in +\link Programmers Chapter 4: Programmers \endlink. + +\index HEADERS!in Project Files +\index SOURCES!in Project Files +\index FORMS!in Project Files +\index TRANSLATIONS!in Project Files + +An example of a complete \c .pro file with four translation source files: +\code + HEADERS = main-dlg.h \ + options-dlg.h + SOURCES = main-dlg.cpp \ + options-dlg.cpp \ + main.cpp + FORMS = search-dlg.ui + TRANSLATIONS = superapp_dk.ts \ + superapp_fi.ts \ + superapp_no.ts \ + superapp_se.ts +\endcode + +\index QApplication!defaultCodec() +\index defaultCodec()!QApplication +\index DEFAULTCODEC!in Project Files +\index Chinese Language +\index Japanese Language + +\l QTextCodec::setCodecForTr() makes it possible to choose a +8-bit encoding for literal strings that appear within \c tr() calls. +This is useful for applications whose source language is, for example, +Chinese or Japanese. If no encoding is set, \c tr() uses Latin-1. + +If you do use the \l QTextCodec::codecForTr() mechanism in your +application, \e {Qt Linguist} needs you to set the \c DEFAULTCODEC +entry in the \c .pro file as well. For example: +\code + DEFAULTCODEC = ISO-8859-5 +\endcode + +\section1 lupdate + +\index lupdate + +Usage: \c {lupdate myproject.pro} + + \index Qt Designer + +This is a simple command line tool. \l lupdate reads a Qt \c .pro +project file, finds the translatable strings in the specified source, +header and \e {Qt Designer} interface files, and produces or updates +the \c .ts translation files listed in the project file. The +translation files are given to the translator who uses \e {Qt +Linguist} to read the files and insert the translations. + +Companies that have their own translators in-house may find it useful +to run \l lupdate regularly, perhaps monthly, as the application +develops. This will lead to a fairly low volume of translation work +spread evenly over the life of the project and will allow the +translators to support a number of projects simultaneously. + +Companies that hire in translators as retquired may prefer to run \l +lupdate only a few times in the application's life cycle, the first +time might be just before the first test phase. This will provide the +translator with a substantial single block of work and any bugs that +the translator detects may easily be included with those found during +the initial test phase. The second and any subsequent \l lupdate runs +would probably take place during the final beta phase. + +\index .ts Files +\index Translation Source Files +\index XML + +The \c .ts file format is a simple human-readable XML format that can +be used with version control systems if retquired. + +\section1 lrelease + +\index lrelease + +Usage: \c {lrelease myproject.pro} + +\index .qm Files +\index Qt Message Files + +This is another simple command line tool. It reads a Qt \c .pro +project file and produces the \c .qm files used by the application, +one for each \c .ts translation source file listed in the project +file. The \c .qm file format is a compact binary format that provides +extremely fast lookups for translations. + +This tool is run whenever a release of the application is to be made, +from initial test version through to final release version. If the \c +.qm files are not created, e.g. because an alpha release is retquired +before any translation has been undertaken, the application will run +perfectly well using the text the programmers placed in the source +files. Once the \c .qm files are available the application will +detect them and use them automatically. + +Note that \l lrelease will only incorporate translations that are +marked as "done". If a translation is missing, or has failed +validation, the original text will be used instead. + +\section1 Missing Translations + +Both \l lupdate and \l lrelease may be used with \c .ts translation +source files which are incomplete. Missing translations will be replaced +with the native language phrases at runtime. diff --git a/tools/linguist/book/linguist-manual.book b/tools/linguist/book/linguist-manual.book new file mode 100644 index 000000000..04dec8713 --- /dev/null +++ b/tools/linguist/book/linguist-manual.book @@ -0,0 +1,90 @@ +\title Guide to the Qt Translation Tools +\granularity chapter + +\chapter Introduction + +Qt provides excellent support for translating applications into local +languages. This Guide explains how to use Qt's translation tools for +each of the roles involved in translating an application. The Guide +begins with a brief overview of the issues that must be considered, +followed by chapters devoted to each role and the supporting tools +provided. + +\link Release... Chapter 2: Release Manager \endlink is aimed at the +person with overall responsibility for the release of the +application. They will typically coordinate the work of the software +engineers and the translator. The chapter describes the use of two +tools. The \l lupdate tool is used to synchronize source code and +translations. The \l lrelease tool is used to create runtime +translation files for use by the released application. + +\link Translators Chapter 3: Translators \endlink is for translators. +It describes the use of the \e {Qt Linguist} tool. No computer +knowledge beyond the ability to start a program and use a text editor +or word processor is retquired. + +\link Programmers Chapter 4: Programmers \endlink is for Qt +programmers. It explains how to create Qt applications that are able +to use translated text. It also provides guidance on how to help the +translator identify the context in which phrases appear. This +chapter's three short tutorials cover everything the programmer needs +to do. + +\section1 Overview of the Translation Process + +Most of the text that must be translated in an application program +consists of either single words or short phrases. These typically +appear as window titles, menu items, pop-up help text (balloon help), +and labels to buttons, check boxes and radio buttons. + +The phrases are entered into the source code by the programmer in +their native language using a simple but special syntax to identify +that the phrases retquire translation. The Qt tools provide context +information for each of the phrases to help the translator, and the +programmer is able to add additional context information to phrases +when necessary. The release manager generates a set of translation +files that are produced from the source files and passes these to the +translator. The translator opens the translation files using \e {Qt +Linguist}, enters their translations and saves the results back into +the translation files, which they pass back to the release manager. +The release manager then generates fast compact versions of these +translation files ready for use by the application. The tools are +designed to be used in repeated cycles as applications change and +evolve, preserving existing translations and making it easy to +identify which new translations are retquired. \e {Qt Linguist} also +provides a phrase book facility to help ensure consistent +translations across multiple applications and projects. + +Translators and programmers must address a number of issues because +of the subtleties and complexities of human language: + +\list +\i A single phrase may need to be translated into several different +forms depending on context, e.g. \e open in English might become \e +\OEFFNEN, "open file", or \e aufbauen, "open internet connection", in +German. +\i Keyboard accelerators may need to be changed but without +introducing conflicts, e.g. "\&Quit" in English becomes "Avslutt" in +Norwegian which doesn't contain a "Q". We cannot use a letter that is +already in use -- unless we change several accelerators. +\i Phrases that contain variables, for example, "The 25 files selected will +take 63 seconds to process", where the two numbers are inserted +programmatically at runtime may need to be reworded because in a +different language the word order and therefore the placement of the +variables may have to change. +\endlist + +The Qt translation tools provide clear and simple solutions to these +issues. + +\RULE + +Please send comments and suggestions regarding this tutorial to the +\link mailto:doc@trolltech.com?subject=Translation_Tutorial Qt doc +team \endlink. Bugs in the tools should be sent to \link +mailto:qt-bugs@trolltech.com?subject=Translation_Tutorial +qt-bugs\endlink. + +\input linguist-manager.leaf +\input linguist-translator.leaf +\input linguist-programmer.leaf diff --git a/tools/linguist/book/linguist-programmer.leaf b/tools/linguist/book/linguist-programmer.leaf new file mode 100644 index 000000000..d74fdf1fe --- /dev/null +++ b/tools/linguist/book/linguist-programmer.leaf @@ -0,0 +1,1145 @@ +\chapter Programmers + +Support for multiple languages is extremely simple in Qt +applications, and adds little overhead to the programmer's workload. + +Qt minimizes the performance cost of using translations by +translating the phrases for each window as they are created. In most +applications the main window is created just once. Dialogs are often +created once and then shown and hidden as retquired. Once the initial +translation has taken place there is no further runtime overhead for +the translated windows. Only those windows that are created, +destroyed and subsequently created will have a translation +performance cost. + +Creating applications that can switch language at runtime is possible +with Qt, but retquires a certain amount of programmer intervention and +will of course incur some runtime performance cost. + +\section1 Making the Application Translation Aware + +Programmers should make their application look for and load the +appropriate translation file and mark user-visible text and Ctrl +keyboard accelerators as targets for translation. + +Each piece of text that retquires translating retquires context to help +the translator identify where in the program the text occurs. In the +case of multiple identical texts that retquire different translations, +the translator also retquires some information to disambiguate the +source texts. Marking text for translation will automatically cause +the class name to be used as basic context information. In some cases +the programmer may be retquired to add additional information to help +the translator. + +\section2 Creating Translation Files + +\index .ts Files +\index Translation Source Files + +Translation files consist of all the user-visible text and Ctrl key +accelerators in an application and translations of that text. +Translation files are created as follows: + +\index lupdate +\index lrelease + +\list 1 +\i Run \l lupdate initially to generate the first set of \c .ts +translation source files with all the user-visible text but no +translations. +\i The \c .ts files are given to the translator who adds translations +using \e {Qt Linguist}. \e {Qt Linguist} takes care of any changed +or deleted source text. +\i Run \l lupdate to incorporate any new text added to the +application. \l lupdate synchronizes the user-visible text from the +application with the translations; it does not destroy any data. +\i Steps 2 and 3 are repeated as often as necessary. +\i When a release of the application is needed \l lrelease is run to +read the \c .ts files and produce the \c .qm files used by the +application at runtime. +\endlist + +\index .pro Files +\index Project Files +\index qmake!Project Files + +For \l lupdate to work successfully, it must know which translation +files to produce. The files are simply listed in the application's \c +.pro Qt project file, for example: +\quotefile tt2/tt2.pro +\skipto TRANSLATIONS +\printline TRANSLATIONS +\printline + +See the \link lupdate "lupdate" \endlink and \link lrelease +"lrelease" \endlink sections. + +\section2 Loading Translations + +\quotefile tt1/main.cpp +\skipto main( +\printline main( +\printuntil QApplication + +\index main() + +This is how a simple \c main() function of a Qt application begins. + +\index QTranslator!load() +\index load()!QTranslator +\index QApplication!installTranslator() +\index installTranslator()!QApplication + +\quotefile tt1/main.cpp +\skipto main( +\printline main( +\printuntil app.installTrans + +For a translation-aware application a translator object is created, a +translation is loaded and the translator object installed into the +application. + +\quotefile tt2/main.cpp +\skipto main( +\printline main( +\printuntil app.installTrans + +In production applications a more flexible approach, for example, +loading translations according to locale, might be more appropriate. If +the \c .ts files are all named according to a convention such as +\e appname_locale, e.g. \c tt2_fr, \c tt2_de etc, then the +code above will load the current locale's translation at runtime. + +If there is no translation file for the current locale the application +will fall back to using the original source text. + +\section2 Making the Application Translate User-Visible Strings + +\index tr() +\index QObject!tr() + +User-visible strings are marked as translation targets by wrapping them +in a \c tr() call, for example: +\code + button = new QPushButton( "&Quit", this ); +\endcode + +would become + +\code + button = new QPushButton( tr("&Quit"), this); +\endcode + +\index Q_OBJECT + +All \l QObject subclasses that use the \c Q_OBJECT macro implement +the \c tr() function. + +Although the \c tr() call is normally made directly since it is +usually called as a member function of a \l QObject subclass, in +other cases an explicit class name can be supplied, for example: + +\code + QPushButton::tr("&Quit") +\endcode + +or + +\code + QObject::tr("&Quit") +\endcode + +\section2 Distinguishing Identical Strings That Retquire Different +Translations + +\index Translation Contexts +\index Contexts!for Translation +\index lupdate + +The \l lupdate program automatically provides a \e context for every +source text. This context is the class name of the class that contains +the \c tr() call. This is sufficient in the vast majority of cases. +Sometimes however, the translator will need further information to +uniquely identify a source text; for example, a dialog that contained +two separate frames, each of which contained an "Enabled" option would +need each identified because in some languages the translation would +differ between the two. This is easily achieved using the +two argument form of the \c tr() call, e.g. + +\code + rbc = new QRadioButton( tr("Enabled", "Color frame"), this ); +\endcode + +and + +\code + rbh = new QRadioButton( tr("Enabled", "Hue frame"), this ); +\endcode + +\index Ctrl Key + +Ctrl key accelerators are also translatable: + +\quotefile tt3/mainwindow.cpp +\skipto tquit() +\printline tquit() +\printuntil Quit + +It is strongly recommended that the two argument form of \c tr() is used +for Ctrl key accelerators. The second argument is the only clue the +translator has as to the function performed by the accelerator. + +\section2 Helping The Translator With Navigation Information + +\index TRANSLATOR!in Comments +\index Translator Comments +\index Comments!for Translators + +In large complex applications it may be difficult for the translator to +see where a particular source text comes from. This problem can be +solved by adding a comment using the keyword \e TRANSLATOR which +describes the navigation steps to reach the text in question; e.g. + +\code + /* TRANSLATOR FindDialog + + Choose Edit|Find from the menu bar or press Ctrl+F to pop up the + Find dialog. + */ +\endcode + +These comments are particularly useful for widget classes. + +\section2 Coping With C++ Namespaces + +\index Namespaces +\index C++!Namespaces +\index lupdate + +C++ namespaces and the \c {using namespace} statement can confuse +\l lupdate. It will interpret \c MyClass::tr() as meaning just +that, not as \c MyNamespace::MyClass::tr(), even if \c MyClass is +defined in the \c MyNamespace namespace. Runtime translation of +these strings will fail because of that. + +\index TRANSLATOR!in Comments +\index Translator Comments +\index Comments!for Translators + +You can work around this limitation by putting a \e TRANSLATOR +comment at the beginning of the source files that use \c +MyClass::tr(): +\code + /* TRANSLATOR MyNamespace::MyClass */ +\endcode +After the comment, all references to \c MyClass::tr() will be +understood as meaning \c MyNamespace::MyClass::tr(). + +\section2 Translating Text that is Outside of a QObject subclass + +\section3 Using QApplication::translate() + +If the quoted text is not in a member function of a QObject subclass, +use either the tr() function of an appropriate class, or the +QApplication::translate() function directly: + +\code + void some_global_function( LoginWidget *logwid ) + { + QLabel *label = new QLabel( + LoginWidget::tr("Password:"), logwid ); + } + + void same_global_function( LoginWidget *logwid ) + { + QLabel *label = new QLabel( + qApp->translate("LoginWidget", "Password:"), + logwid ); + } +\endcode + +\section3 Using QT_TR_NOOP() and QT_TRANSLATE_NOOP() + +If you need to have translatable text completely outside a function, +there are two macros to help: QT_TR_NOOP() and QT_TRANSLATE_NOOP(). +These macros merely mark the text for extraction by \l{lupdate}. +The macros expand to just the text (without the context). + +Example of QT_TR_NOOP(): +\code + QString FriendlyConversation::greeting( int greet_type ) + { + static const char* greeting_strings[] = { + QT_TR_NOOP( "Hello" ), + QT_TR_NOOP( "Goodbye" ) + }; + return tr( greeting_strings[greet_type] ); + } +\endcode + +Example of QT_TRANSLATE_NOOP(): +\code + static const char* greeting_strings[] = { + QT_TRANSLATE_NOOP( "FriendlyConversation", "Hello" ), + QT_TRANSLATE_NOOP( "FriendlyConversation", "Goodbye" ) + }; + + QString FriendlyConversation::greeting( int greet_type ) + { + return tr( greeting_strings[greet_type] ); + } + + QString global_greeting( int greet_type ) + { + return qApp->translate( "FriendlyConversation", + greeting_strings[greet_type] ); + } +\endcode + +\section1 Tutorials + +Three tutorials are presented. The first demonstrates the creation of +a \l QTranslator object. It also shows the simplest use of the \c +tr() function to mark user-visible source text for translation. The +second tutorial explains how to make the application load the +translation file applicable to the current locale. It also shows the +use of the two-argument form of \c tr() which provides additional +information to the translator. The third tutorial explains how +identical source texts can be distinguished even when they occur in +the same context. This tutorial also discusses how the translation +tools help minimize the translator's work when an application is +upgraded. + +\section2 Tutorial 1: Loading and Using Translations + +\img tt1_en.png +\caption Tutorial 1 Screenshot, English version + +\include tt1/tt1.pro +\caption \c tt1.pro + +\include tt1/main.cpp +\caption \c main.cpp + +This example is a reworking of the \link tutorial1-01.html +"hello-world" \endlink example from \link tutorial.html Tutorial +#1\endlink, with a Latin translation. The \e {Tutorial 1 Screenshot, +English version}, above, shows the English version. + +\quotefile tt1/main.cpp + +\section3 Line by Line Walk-through + +\quotefile tt1/main.cpp + +\skipto qtranslator +\printline qtranslator + +\index QTranslator + +This line includes the definition of the \l QTranslator class. +Objects of this class provide translations for user-visible text. + +\skipto QTranslator +\printuntil tor + +Creates a \l QTranslator object without a parent. + +\printline load + +\index tt1_la.qm + +Tries to load a file called \c tt1_la.qm (the \c .qm file extension is +implicit) that contains Latin translations for the source texts used in +the program. No error will occur if the file is not found. + +\index QApplication!installTranslator() +\index installTranslator()!QApplication + +\printline installTranslator + +Adds the translations from \c tt1_la.qm to the pool of translations used +by the program. + +\index Hello World + +\printline hello + +Creates a push button that displays "Hello world!". If \c tt1_la.qm +was found and contains a translation for "Hello world!", the +translation appears; if not, the source text appears. + +\index tr() +\index QObject!tr() + +All classes that inherit \l QObject have a \c tr() function. Inside +a member function of a \l QObject class, we simply write \c tr("Hello +world!") instead of \c QPushButton::tr("Hello world!") or \c +QObject::tr("Hello world!"). + +\section3 Running the Application in English + +\index English Language + +Since we haven't made the translation file \c tt1_la.qm, the source text +is shown when we run the application: + +\img tt1_en.png +\caption Tutorial 1 Screenshot, English version + +\section3 Creating a Latin Message File + +\index tt1.pro +\index Latin + +The first step is to create a project file, \c tt1.pro, that lists +all the source files for the project. The project file can be a qmake +project file, or even an ordinary makefile. Any file that contains + +\index SOURCES!in Project Files +\index TRANSLATIONS!in Project Files + +\quotefile tt1/tt1.pro +\skipto SOURCES +\printline SOURCES +\skipto TRANSLATIONS +\printline TRANSLATIONS + +will work. \e TRANSLATIONS specifies the message files we want to +maintain. In this example, we just maintain one set of translations, +namely Latin. + +\index .ts Files +\index Translation Source Files +\index .qm Files +\index Qt Message Files + +Note that the file extension is \c .ts, not \c .qm. The \c .ts +translation source format is designed for use during the +application's development. Programmers or release managers run the \l +lupdate program to generate and update \c .ts files with the source +text that is extracted from the source code. Translators read and +update the \c .ts files using \e {Qt Linguist} adding and editing +their translations. + +\index XML + +The \c .ts format is human-readable XML that can be emailed directly +and is easy to put under version control. If you edit this file +manually, be aware that the default encoding for XML is UTF-8, not +Latin-1 (ISO 8859-1). One way to type in a Latin-1 character such as +'\OSLASH' (Norwegian o with slash) is to use an XML entity: +"\ø". This will work for any Unicode character. + +Once the translations are complete the \l lrelease program is used to +convert the \c .ts files into the \c .qm Qt message file format. The +\c .qm format is a compact binary format designed to deliver very +fast lookup performance. Both \l lupdate and \l lrelease read all the +project's source and header files (as specified in the HEADERS and +SOURCES lines of the project file) and extract the strings that +appear in \c tr() function calls. + +\index lupdate + +\l lupdate is used to create and update the message files (\c tt1_la.ts +in this case) to keep them in sync with the source code. It is safe to +run \l lupdate at any time, as \l lupdate does not remove any +information. For example, you can put it in the makefile, so the \c .ts +files are updated whenever the source changes. + +\index .ts Files +\index Translation Source Files +\index XML + +Try running \l lupdate right now, like this: +\code + lupdate -verbose tt1.pro +\endcode +(The \c -verbose option instructs \c lupdate to display messages that +explain what it is doing.) You should now have a file \c tt1_la.ts in +the current directory, containing this: +\code + + + QPushButton + + Hello world! + + + + +\endcode +You don't need to understand the file format since it is read and +updated using tools (\l lupdate, \e {Qt Linguist}, \l lrelease). + +\section3 Translating to Latin with Qt Linguist + +\index Qt Linguist +\index Linguist + +We will use \e {Qt Linguist} to provide the translation, although +you can use any XML or plain text editor to enter a translation into a +\c .ts file. + +To start \e {Qt Linguist}, type +\code + linguist tt1_la.ts +\endcode + +You should now see the text "QPushButton" in the top left pane. +Double-click it, then click on "Hello world!" and enter "Orbis, te +saluto!" in the \e Translation pane (the middle right of the +window). Don't forget the exclamation mark! + +Click the \e Done checkbox and choose \e File|Save from the +menu bar. The \c .ts file will no longer contain +\code + +\endcode +but instead will have +\code + Orbis, te saluto! +\endcode + +\section3 Running the Application in Latin + +\index Latin +\index lrelease + +To see the application running in Latin, we have to generate a \c .qm +file from the \c .ts file. Generating a \c .qm file can be achieved +either from within \e {Qt Linguist} (for a single \c .ts file), or +by using the command line program \l lrelease which will produce one \c +.qm file for each of the \c .ts files listed in the project file. +Generate \c tt1_la.qm from \c tt1_la.ts by choosing +\e File|Release from \e {Qt Linguist}'s menu bar and pressing +\e Save in the file save dialog that pops up. Now run the \e tt1 example +program again. This time the button will be labelled "Orbis, te +saluto!". + +\img tt1_la.png +\caption Tutorial 1 Screenshot, Latin version + +\section2 Tutorial 2: Using Two or More Languages + +\img tt2_en.png +\caption Tutorial 2 Screenshot, English version + +\index .pro Files +\index Project Files +\index qmake!Project Files + +\include tt2/tt2.pro +\caption tt2.pro + +\index Translation Contexts +\index Contexts!for Translation + +This example is a slightly more involved and introduces a key +\e {Qt Linguist} concept: "contexts". + +\list +\i \c arrowpad.h contains the definition of \c ArrowPad, a custom widget; +\i \c arrowpad.cpp contains the implementation of \c ArrowPad; +\i \c mainwindow.h contains the definition of \c MainWindow, a subclass of + \l QMainWindow +\i \c mainwindow.cpp contains the implementation of \c MainWindow; +\i \c main.cpp contains main(). +\endlist + +\index tt2.pro +\index French Language +\index Dutch Language + +We will use two translations, French and Dutch, although there is no +effective limit on the number of possible translations that can be used +with an application. The relevant lines of \c tt2.pro are + +\quotefile tt2/tt2.pro +\skipto HEADERS +\printuntil tt2_nl.ts + +\index lupdate +\index tt2_fr.ts +\index tt2_nl.ts + +Run \l lupdate; it should produce two identical message files +\c tt2_fr.ts and \c tt2_nl.ts. These files will contain all the source +texts marked for translation with \c tr() calls and their contexts. + +\section3 Line by Line Walk-through + +\index ArrowPad!in Translation Tutorial +\index English Language + +In \c arrowpad.h we define the \c ArrowPad subclass which is a +subclass of \l QWidget. In the \e {Tutorial 2 Screenshot, English +version}, above, the central widget with the four buttons is an +\c ArrowPad. + +\quotefile tt2/arrowpad.h +\skipto class ArrowPad +\printline class ArrowPad + +\index Q_OBJECT +\index tr() +\index QObject!tr() +\index Translation Contexts +\index Contexts!for Translation + +When \l lupdate is run it not only extracts the source texts but it +also groups them into contexts. A context is the name of the class in +which the source text appears. Thus, in this example, "ArrowPad" is a +context: it is the context of the texts in the \c ArrowPad class. +The \c Q_OBJECT macro defines \c tr(x) in \c ArrowPad like this + +\index QApplication!translate() +\index translate()!QApplication + +\code + qApp->translate( "ArrowPad", x ) +\endcode + +Knowing which class each source text appears in enables \e {Qt +Linguist} to group texts that are logically related together, e.g. +all the text in a dialog will have the context of the dialog's class +name and will be shown together. This provides useful information for +the translator since the context in which text appears may influence how +it should be translated. For some translations keyboard +accelerators may need to be changed and having all the source texts in a +particular context (class) grouped together makes it easier for the +translator to perform any accelerator changes without introducing +conflicts. + +In \c arrowpad.cpp we implement the \c ArrowPad class. + +\quotefile tt2/arrowpad.cpp +\skipto QPushButton +\printline QPushButton + +We call \c ArrowPad::tr() for each button's label since the labels are +user-visible text. + +\img tt2_en.png +\caption Tutorial 2 Screenshot, English version + +\index Q_OBJECT +\index MainWindow!in Translation Tutorial + +\quotefile tt2/mainwindow.h +\skipto QMainWindow +\printline QMainWindow +\printuntil Q_OBJECT + +In the \e {Tutorial 2 Screenshot, English version}, above, the whole +window is a \c MainWindow. This is defined in the \c mainwindow.h +header file. Here too, we use \c Q_OBJECT, so that \c MainWindow will +become a context in \e {Qt Linguist}. + +In the implementation of \c MainWindow, \c mainwindow.cpp, we create +an instance of our \c ArrowPad class + +\quotefile tt2/mainwindow.cpp +\skipto arrow pad +\printline arrow pad + +We also call \c MainWindow::tr() twice, once for the menu item and +once for the accelerator. + +\index Ctrl Key +\index Alt Key + +\skipto tquit() +\printline tquit() +\printuntil Ctrl+Q + +Note the use of \c tr() to support different keys in other languages. +"Ctrl+Q" is a good choice for Quit in English, but a Dutch translator +might want to use "Ctrl+A" (for Afsluiten) and a German translator +"Strg+E" (for Beenden). When using \c tr() for Ctrl key accelerators, +the two argument form should be used with the second argument +describing the function that the accelerator performs. + +\index main() + +Our \c main() function is defined in \c main.cpp as usual. + +\quotefile tt2/main.cpp +\skipto QTranslator +\printline QTranslator +\printuntil install + +\index QTextCodec!locale() +\index locale()!QTextCodec +\index LANG!Environment Variable +\index Environment Variables!LANG + +We choose which translation to use according to the current locale. +\l QTextCodec::locale() can be influenced by setting the \c LANG +environment variable, for example. Notice that the use of a naming +convention that incorporates the locale for \c .qm message files, +(and \c .ts files), makes it easy to implement choosing the +translation file according to locale. + +If there is no \c .qm message file for the locale chosen the original +source text will be used and no error raised. + +\section3 Translating to French and Dutch + +We'll begin by translating the example application into French. Start +\e {Qt Linguist} with \c tt2_fr.ts. You should get the seven source +texts ("\&Up", "\&Left", etc.) grouped in two contexts ("ArrowPad" +and "MainWindow"). + +Now, enter the following translations: + +\list +\i \c ArrowPad + \list + \i \&Up - \&Haut + \i \&Left - \&Gauche + \i \&Right - \&Droite + \i \&Down - \&Bas + \endlist +\i \c MainWindow + \list + \i E\&xit - \&Quitter + \i Ctrl+Q - Ctrl+Q + \i \&File - \&Fichier + \endlist +\endlist + +It's tquickest to press \Key Alt+D (which clicks the \e {Done \& Next} +button) after typing each translation, since this marks the +translation as done and moves on to the next source text. + +Save the file and do the same for Dutch working with \c tt2_nl.ts: + +\list +\i \c ArrowPad + \list + \i \&Up - \&Boven + \i \&Left - \&Links + \i \&Right - \&Rechts + \i \&Down - \&Onder + \endlist +\i \c MainWindow + \list + \i E\&xit - \&Afsluiten + \i Ctrl+Q - Ctrl+A + \i File - \&Bestand + \endlist +\endlist + +We have to convert the \c tt1_fr.ts and \c tt1_nl.ts translation source +files into \c .qm files. We could use \e {Qt Linguist} as we've done +before; however using the command line tool \l lrelease ensures that +\e all the \c .qm files for the application are created without us +having to remember to load and \e File|Release each one +individually from \e {Qt Linguist}. + +In practice we would include calls to \l lupdate and \l lrelease in the +application's makefile to ensure that the latest translations are +used. + +\omit +an example of a makefile or .pro file that did this would be nice +\endomit + +Type + +\code + lrelease tt2.pro +\endcode + +\index LANG!Environment Variable +\index export!Unix Command +\index setenv!Unix Command + +This should create both \c tt2_fr.qm and \c tt2_nl.qm. Set the \c +LANG environment variable to \c fr. In Unix, one of the two following +commands should work + +\code + export LANG=fr + setenv LANG fr +\endcode + +\index + +\index autoexec.bat +\index set!Windows Command + +In Windows, either modify \c autoexec.bat or run + +\code + set LANG=fr +\endcode + +When you run the program, you should now see the French version: + +\img tt2_fr.png +\caption Tutorial 2 Screenshot, French version + +Try the same with Dutch, by setting \c LANG=nl. Now the Dutch +version should appear: + +\img tt2_nl.png +\caption Tutorial 2 Screenshot, Dutch version + +\section3 Exercises + +Mark one of the translations in \e {Qt Linguist} as not done, i.e. +by unchecking the "done" checkbox; run \l lupdate, then \l lrelease, +then the example. What effect did this change have? + +\index Canada +\index French Canada + +Set \c LANG=fr_CA (French Canada) and run the example program again. +Explain why the result is the same as with \c LANG=fr. + +Change one of the accelerators in the Dutch translation to eliminate the +conflict between \e \&Bestand and \e \&Boven. + + +\section2 Tutorial 3: Disambiguating Identical Strings + +\img tt3_10_en.png +\caption Tutorial 3 Screenshot, "Troll Print 1.0", English version + +\include tt3/tt3.pro +\caption \c tt3.pro + +\index Portuguese Language +\index Brazilian Language + +We've included a translation file, \c tt3_pt.ts, which contains some +Portuguese translations for this example. + +\index Troll Print + +We will consider two releases of the same application: Troll Print +1.0 and 1.1. We will learn to reuse the translations created for one +release in a subsequent release. (In this tutorial, you need to edit +some source files. It's probably best to copy all the files to a new +temporary directory and work from there.) + +Troll Print is a toy example application that lets the user choose +printer settings. It comes in two versions: English and Portuguese. + +Version 1.0 consists of these files: + +\index tt3.pro +\index tt3_pt.ts + +\list +\i \c printpanel.h contains the definition of PrintPanel; +\i \c printpanel.cpp contains the implementation of PrintPanel; +\i \c mainwindow.h contains the definition of \c MainWindow; +\i \c mainwindow.cpp contains the implementation of \c MainWindow; +\i \c main.cpp contains main(); +\i \c tt3.pro is the \e qmake project file. +\i \c tt3_pt.ts is the Portuguese message file. +\endlist + +\section3 Line by Line Walk-through + +The PrintPanel is defined in \c printpanel.h. + +\quotefile tt3/printpanel.h +\skipto QVBox +\printline QVBox +\printuntil Q_OBJECT + +\index Q_OBJECT + +\index PrintPanel!in Translation Tutorial + +PrintPanel is a \l QWidget. It needs the \c Q_OBJECT macro for \c +tr() to work properly. + +The implementation file is \c printpanel.cpp. + +\quotefile tt3/printpanel.cpp +\skipto setSpacing +\skipto / +\printline / +\printline +\printline +\printline + +\index Troll Print + +Some of the code is commented out in Troll Print 1.0; you will uncomment +it later, for Troll Print 1.1. + +\quotefile tt3/printpanel.cpp +\skipto twoSided +\printline twoSided +\printuntil toggle +\printline +\printuntil toggle + +Notice the two occurrences of \c tr("Enabled") and of \c +tr("Disabled") in PrintPanel. Since both "Enabled"s and "Disabled"s +appear in the same context \e {Qt Linguist} will only display one +occurrence of each and will use the same translations for the +duplicates that it doesn't display. Whilst this is a useful +timesaver, in some languages, such as Portuguese, the second +occurrence retquires a separate translation. We will see how \e {Qt +Linguist} can be made to display all the occurrences for separate +translation shortly. + +\index MainWindow!in Translation Tutorial + +The header file for \c MainWindow, \c mainwindow.h, contains no +surprises. In the implementation, \c mainwindow.cpp, we have some +user-visible source texts that must be marked for translation. + +\quotefile tt3/mainwindow.cpp +\skipto setCaption +\printline setCaption + +We must translate the window's caption. + +\skipto tquit +\printline tquit +\printuntil Help + +We also need to translate the menu items. Note that the two argument +form of \c tr() is used for the keyboard accelerator, "Ctrl+Q", since +the second argument is the only clue the translator has to indicate +what function that accelerator will perform. + +\quotefile tt3/main.cpp +\skipto QTranslator +\printuntil installTranslator + +\index main() + +The \c main() function in \c main.cpp is the same as the one in \link +{Tutorial 2...} Tutorial 2 \endlink. In particular it chooses a +translation file based on the current locale. + +\section3 Running Troll Print 1.0 in English and in Portuguese + +We will use the translations in the \c tt3_pt.ts file that is provided. + +Set the \c LANG environment variable to \c pt, and then run \c tt3. +You should still see the English version, as shown in the \e +{Tutorial 3 Screenshot, "Troll Print 1.0", English version}, above. +Now run \l lrelease, e.g. \c {lrelease tt3.pro}, and then run the +example again. Now you should see the Portuguese edition (Troll +Imprimir 1.0): + +\img tt3_10_pt_bad.png +\caption Tutorial 3 Screenshot, "Troll Imprimir 1.0", (Bad) Portuguese version + +Whilst the translation has appeared correctly, it is in fact wrong. In +good Portuguese, the second occurrence of "Enabled" should be +"Ativadas", not "Ativado" and the ending for the second translation of +"Disabled" must change similarly too. + +If you open \c tt3_pt.ts using \e {Qt Linguist}, you will see that +there is just one occurrence of "Enabled" and of "Disabled" in the +translation source file, even though there are two of each in the +source code. This is because \e {Qt Linguist} tries to minimize the +translator's work by using the same translation for duplicate source +texts. In cases such as this where an identical translation is wrong, +the programmer must disambiguate the duplicate occurrences. This is +easily achieved by using the two argument form of \c tr(). + +We can easily determine which file must be changed because the +translator's "context" is in fact the class name for the class where +the texts that must be changed appears. In this case the file is \c +printpanel.cpp, where the there are four lines to change. Add the +second argument "two-sided" in the appropriate \c tr() calls to the +first pair of radio buttons: + +\code + but = new QRadioButton( tr("Enabled", "two-sided"), twoSided ); + but = new QRadioButton( tr("Disabled", "two-sided"), twoSided ); +\endcode + +and add the second argument "colors" in the appropriate \c tr() calls +for the second pair of radio buttons: + +\code + but = new QRadioButton( tr("Enabled", "colors"), colors ); + but = new QRadioButton( tr("Disabled", "colors"), colors ); +\endcode + +\index lupdate +\index tt3_pt.ts + +Now run \l lupdate and open \c tt3_pt.ts with \e {Qt Linguist}. You +should now see two changes. + +First, the translation source file now contains \e three "Enabled", +"Disabled" pairs. The first pair is marked "(obs.)" signifying that they +are obsolete. This is because these texts appeared in \c tr() calls that +have been replaced by new calls with two arguments. The second pair has +"two-sided" as their comment, and the third pair has "colors" as their +comment. The comments are shown in the \e {Source text and comments} +area in \e {Qt Linguist}. + +Second, the translation text "Ativado" and "Desativado" have been +automatically used as translations for the new "Enabled" and "Disabled" +texts, again to minimize the translator's work. Of course in this case +these are not correct for the second occurrence of each word, but they +provide a good starting point. + +Change the second "Ativado" into "Ativadas" and the second +"Desativado" into "Desativadas", then save and tquit. Run \l lrelease +to obtain an up-to-date binary \c tt3_pt.qm file, and run Troll Print +(or rather Troll Imprimir). + +\img tt3_10_pt_good.png +\caption Tutorial 3 Screenshot, "Troll Imprimir 1.0", (Good) Portuguese version + +\index Translator Comments +\index Comments!for Translators + +The second argument to \c tr() calls, called "comments" in \e {Qt +Linguist}, distinguish between identical source texts that occur in +the same context (class). They are also useful in other cases to give +clues to the translator, and in the case of Ctrl key accelerators are +the only means of conveying the function performed by the accelerator to +the translator. + +\index TRANSLATOR!in Comments +\index Translator Comments +\index Comments!for Translators + +An additional way of helping the translator is to provide information on +how to navigate to the particular part of the application that contains +the source texts they must translate. This helps them see the context +in which the translation appears and also helps them to find and test +the translations. This can be achieved by using a \e TRANSLATOR comment +in the source code: +\code + /* TRANSLATOR MainWindow + + In this application the whole application is a MainWindow. + Choose Help|About from the menu bar to see some text + belonging to MainWindow. + */ +\endcode + +Try adding these comments to some source files, particularly to +dialog classes, describing the navigation necessary to reach the +dialogs. You could also add them to the example files, e.g. \c +mainwindow.cpp and \c printpanel.cpp are appropriate files. Run \l +lupdate and then start \e {Qt Linguist} and load in \c tt3_pt.ts. +You should see the comments in the \e {Source text and comments} area +as you browse through the list of source texts. + +Sometimes, particularly with large programs, it can be difficult for +the translator to find their translations and check that they're +correct. Comments that provide good navigation information can save +them time: + +\code + /* TRANSLATOR ZClientErrorDialog + + Choose Client|Edit to reach the Client Edit dialog, then choose + Client Specification from the drop down list at the top and pick + client Bartel Leendert van der Waerden. Now check the Profile + checkbox and then click the Start Processing button. You should + now see a pop up window with the text "Error: Name too long!". + This window is a ZClientErrorDialog. + */ +\endcode + + +\section3 Troll Print 1.1 + +We'll now prepare release 1.1 of Troll Print. Start your favorite text +editor and follow these steps: + +\list +\i Uncomment the two lines that create a \l QLabel with the text + "\TROLL PRINT\" in \c printpanel.cpp. +\i Word-tidying: Replace "2-sided" by "Two-sided" in \c printpanel.cpp. +\i Replace "1.0" with "1.1" everywhere it occurs in \c mainwindow.cpp. +\i Update the copyright year to 1999-2000 in \c mainwindow.cpp. +\endlist + +(Of course the version number and copyright year would be consts or +#defines in a real application.) + +Once finished, run \l lupdate, then open \c tt3_pt.ts in \e {Qt +Linguist}. The following items are of special interest: + +\list +\i \c MainWindow + \list + \i Troll Print 1.0 - marked "(obs.)", obsolete + \i About Troll Print 1.0 - marked "(obs.)", obsolete + \i Troll Print 1.0. Copyright 1999 Macroshaft, Inc. - + marked "(obs.)", obsolete + \i Troll Print 1.1 - automatically translated as + "Troll Imprimir 1.1" + \i About Troll Print 1.1 - automatically translated as + "Troll Imprimir 1.1" + \i Troll Print 1.1. Copyright 1999-2000 Macroshaft, + Inc. - automatically translated as "Troll Imprimir 1.1. + Copyright 1999-2000 Macroshaft, Inc." + \endlist +\i \c PrintPanel + \list + \i 2-sided - marked "(obs.)", obsolete + \i \TROLL PRINT\ - unmarked, i.e. untranslated + \i Two-sided - unmarked, i.e. untranslated. + \endlist +\endlist + +Notice that \l lupdate works hard behind the scenes to make revisions +easier, and it's pretty smart with numbers. + +Go over the translations in \c MainWindow and mark these as "done". +Translate "\TROLL PRINT\" as "\TROLL IMPRIMIR\". +When you're translating "Two-sided", press the \e {Guess Again} +button to translate "Two-sided", but change the "2" into "Dois". + +Save and tquit, then run \l lrelease. The Portuguese version +should look like this: + +\img tt3_11_pt.png +\caption Tutorial 3 Screenshot, "Troll Imprimir 1.1", Portuguese version + +Choose \e{Ajuda|Sobre}, (\e{Help|About}), to see the about box + +\img tt3_11_about_pt.png +\caption Tutorial 3 Screenshot, About box, Portuguese version + +\index English Language +\index Translating Qt +\index Qt!Translating Qt + +If you choose \e {Ajuda|Sobre Qt}, (\e {Help|About Qt}), you'll get +an English dialog. Oops! Qt itself needs to be translated. See the +document \link i18n.html#qt-itself Internationalization with Qt +\endlink for details. + +Now set \c LANG=en to get the original English version: + +\img tt3_11_en.png +\caption Tutorial 3 Screenshot, "Troll Print 1.1", English version + +\section2 Summary + +These tutorials cover all that you need to know to prepare your Qt +applications for translation. + +At the beginning of a project add the translation source files to be +used to the project file and add calls to \l lupdate and \l lrelease to +the make file. + +During the project all the programmer must do is wrap any user-visible +text in \c tr() calls. They should also use the two argument form for +Ctrl key accelerators, or when asked by the translator for the cases +where the same text translates into two different forms in the same +context. The programmer should also include \e TRANSLATION comments to +help the translator navigate the application. diff --git a/tools/linguist/book/linguist-translator.leaf b/tools/linguist/book/linguist-translator.leaf new file mode 100644 index 000000000..e20d7921a --- /dev/null +++ b/tools/linguist/book/linguist-translator.leaf @@ -0,0 +1,582 @@ +\chapter Translators + +\img linguist.png +\caption Linguist Main Window + +\section1 The One Minute Guide to Using Qt Linguist + +\index Linguist +\index Qt Linguist +\index Contexts!for Translation + +\e {Qt Linguist} is a tool for adding translations to Qt +applications. It introduces the concept of a translation "context" +which means a group of phrases that appear together on the screen +e.g. in the same menu or dialog. + +To start, run \e {Qt Linguist}, either from the taskbar menu, or by +double clicking the desktop icon, or type \c {linguist} (followed by +\Key Enter) at the command line. Once \e {Qt Linguist} has started +choose \Menu File|Open from the menu bar and select a \c .ts +translation source file to work on. + +\e {Qt Linguist}'s main window is divided into four main areas. The +left hand side contains the Context list, the top right is the Source +text area, the middle right is the translation area and the bottom +right is the phrases and guesses area. We'll describe them in detail +later. + +Click on one of the contexts in the context list (left hand side) and +then click on one of the phrases that appears in the Source text area +(top right). The phrase will be copied into the translation area +(middle right). Click under the word 'Translation' and type in the +translation. Click \Key Ctrl+Enter (Done \& Next) to confirm that you +have completed the translation and to move on to the next phrase that +retquires translation. + +The cycle of entering a translation then pressing \Key Ctrl+Enter can +be repeated until all the translations are done or until you finish +the session. Linguist will attempt to fill the "phrases and guesses" +area with possible translations from any open phrase books and any +previous translations. Each has a keyboard shortcut, e.g. +\Key Ctrl+1, \Key Ctrl+2, etc., which you can use to copy the +guess into the Translation area. (Mouse users can double click a +phrase or guess to move it into the Translation area.) At the end of +the session choose \Menu File|Save from the menu bar and then +\Menu File|Exit to tquit. + +\section1 Qt Linguist's Main Window + +\section2 Context List + +\index Contexts!for Translation + +This appears at the left hand side of the main window by default. The +first column, 'Done', identifies whether or not the translations for the +context have been done. A tick indicates that all the translations have +been done and are valid. A question mark indicates that one or more +translations have not been done or have failed validation. The second +column, 'Context' is the name of the context in which the translation +phrases appear. The third column, 'Items' shows two numbers, the first +is the number of translations that have been done, and the second is the +number of phrases that are in the context; if the numbers are equal then +all the translations have been done. Note that a greyed out tick +indicates an obsolete translation, i.e. a phrase that was translated in +a previous version of the application but which does not occur in the +new version. + +The contexts are ordered alphabetically. The phrases within each context +are in the order in which they appear in the source program and this may +not be the order in which they are shown on screen. + +The Context List is a dockable window so it can be dragged to another +position in the main window, or dragged out of the main window to be a +window in its own right. If you move the Context List, \e {Qt +Linguist} will remember its position and restore it whenever you +start the program. + +\section2 Source Text Area + +This appears at the top right of the main window by default. The first +column, 'Done', signifies the status of the translation. A tick +indicates that the phrase has been translated and passed validation. A +question mark indicates that the translation has not been done. An +exclamation mark indicates that the translation has failed validation. +The second column 'Source text' shows the text that must be translated. +The third column shows the translation. + +\e{Qt Linguist} provides three kinds of validation: accelerator, +punctuation and phrase. If the source text contains an accelerator +i.e. an ampersand, '\&' and the translated text does not contain an +ampersand the translation will fail the accelerator validation. +Similarly, if the source text ends with a particular punctuation +mark, e.g. '?', '!' or '.' and the translation ends with a different +punctuation mark the translation will fail the punctuation +validation. If the source text has a translation in one of the open +phrase books that differs from the translation used the translation +will fail phrase validation. (See \l Validation.) + +The Source Text Area is a dockable window. + +\section2 Translation Area + +This area appears at the middle right of the main window by default. It +is comprised of three vertical sections. The first section is labelled +'Source text' below which the source text appears. The second section +contains contextual information on a light blue background that the +programmer has added to assist the translator. If no contextual +information has been given this section does not appear. The third +section is labelled 'Translation' and this is where you enter the +translation of the source text. + +\section2 Phrases and Guesses Area + +\index Phrases!in Qt Linguist +\index Guesses!in Qt Linguist + +This area appears at the bottom right of the main window by default. +When you move to a new phrase if the phrase is in one of the phrase +books that has been loaded the phrase will appear in this area with its +translation. If the phrase is the same or similar to another phrase that +has already been translated the phrase and translation will be shown in +this area. To copy a translation from the phrases and guesses area press +\Key F6 to move to the phrases and guesses area, use the up and down arrow +keys to move to the phrase you want to use and press Enter to copy it. +If you decide that you don't want to copy a phrase after all, press Esc. +In both cases the focus will return to the Translation area. +Alternatively, double click the translation you want to use and it will +be copied into the translation area. + +The Phrases and Guesses Area is a dockable window. + +\section1 Common Tasks + +\section2 Leaving a Translation for Later + +If you wish to leave a translation press \Key Ctrl+L (Next Unfinished) to +move to the next unfinished translation. An unfinished translation is +one that either has not been translated at all or one which fails +validation. To move to the next phrase press \Key Shift+Ctrl+L. You can also +navigate using the Translation menu. If you want to go to a different +context entirely, click the context you want to work on in the Context +list, then click the source text in the Source Text area. + +\section2 Phrases That Retquire Multiple Translations Depending on Context + +\index Contexts!for Translation +\index Comments!for Translators + +The same phrase may occur in two or more contexts without conflict. Once +a phrase has been translated in one context, \e {Qt Linguist} notes +that the translation has been made and when the translator reaches a +later occurrence of the same phrase \e {Qt Linguist} will provide +the previous translation as a possible translation candidate in the +phrases and guesses area. If the +previous translation is acceptable just click the \e {Done \& Next} +button (press \Key Ctrl+Enter) to move on to the next unfinished phrase. + +If a phrase occurs more than once in a particular context it will only +be shown once in \e {Qt Linguist}'s context list and +the translation will be applied to every occurrence within the context. +If the same phrase needs to be translated differently within the same +context the programmer must provide a distinguishing comment for each of +the phrases concerned. If such comments are used the duplicate phrases +will appear in the context list. The programmers comments will appear in +the translation area on a light blue background. + +\section2 Changing Keyboard Accelerators + +\index Accelerators +\index Keyboard Accelerators + +A keyboard accelerator is a key combination that when pressed will +cause an application to perform an action. Keyboard accelerators +normally come in two forms: Alt key and Ctrl key accelerators. + +\index Alt Key + +Alt key accelerators are used for menus and buttons. The underlining +signifies that pressing the Alt key with the underlined letter is the +same as clicking the menu item with the mouse. For example, most +applications have a \e File menu with the "F" in the word "file" +underlined. In these applications the file menu can be invoked either by +clicking the word "File" on the menu bar or by pressing Alt+F. The +accelerator key which is underlined is signified by preceeding it with +an ampersand, e.g. \e \&File. If a source phrase appears with an +ampersand in it then the translation should also contain an ampersand, +preferably in front of the same letter. The meaning of Alt key +accelerators can be determined from the phrase in which the ampersand is +embedded. The translator may need to change the letter used with the Alt +key, e.g. if the translated phrase does not contain the original +accelerator letter. Conflicts with other keys, i.e. having two Alt key +accelerators using the same letter in the same context, must be avoided. +Note that some Alt key accelerators, usually those on the menu bar, may +apply in other contexts. + +\index Ctrl Key + +Ctrl key accelerators can exist independently of any visual control. +They are often used to invoke actions in menus that would otherwise +take several keystrokes or mouse clicks. They may also be used to +perform actions that do not appear in any menu or on any button. For +example, most applications that have a \e File menu have a submenu +item called \e New. In many applications this will appear as "\NEW +Ctrl+N". This menu option could be invoked by clicking \e File then +clicking \e New with the mouse. Or you could press Alt+F then press N +since these letters are underlined. But the same thing can be achieved +simply by pressing \Key Ctrl+N. Accelerators that use the Ctrl key are +shown literally in the source text, e.g. \Key Ctrl+Enter. Ctrl key +accelerators have no phrase so the translator \index Comments!for +Translators must rely on the programmer to add a "comment" which +appears in the top right hand pane. This comment should explain what +action the Ctrl key accelerator performs. Ideally Ctrl key +accelerators are translated simply by copying them by chossing the \e +{Begin from Source} entry in the \Menu Translations menu. However in +some cases the letter will not make sense in the target language and +must be changed. Whatever letter (or digit) is chosen, the translation +should always be in the form "Ctrl+" followed by the letter or digit +in upper case. As with Alt key accelerators, if the translator changes +the key it must not conflict with any other Ctrl key accelerator. + +Later versions of \e {Qt Linguist} are expected to help the +translator avoid accelerator conflicts. + +\section2 Dealing with Phrases that Contain Variables + +Some phrases contain variables. Variables are placeholders for items of +text that are filled in at runtime. They are signified in the source +text with a percent sign followed by a digit, e.g. \e {After processing +file %1, file %2 is next in line}. In this example, \c %1 will be +replaced at runtime with the name of the first file to be processed and +\c %2 with the name of the next file to be processed. In the translated +version the variables must still appear. For example a German +translation might reverse the phrases, e.g. \e {Datei %2 wird +bearbeitet, wenn. Datei %1 fertig ist}. Note that both variables +are still used but their order has changed. The order in which variables +appear does not matter; \c %1 will always be replaced by the same text +at runtime no matter where it appears in the source text or translation +and similarly \c %2, etc. + +\section2 Reusing Translations + +If the translated text is similar to the source text, choose the \e +{Begin from Source} entry in the \Menu Translations menu (press \Key +Ctrl+B) which will copy the source text into the translation area. + +\e {Qt Linguist} automatically lists phrases from the open phrase +books and similar or identical phrases that have already been translated +in the Phrases and guesses area. + +\section1 Creating and Using Phrase Books + +\index Phrases!in Qt Linguist +\index Phrase Books + +\img phrasebookdialog.png +\caption Phrase Book Dialog + +A \e {Qt Linguist} phrase book is a set of source phrases, target +(translated) phrases, and optional definitions. Phrase Books are created +independently of any application, although typically one phrase book +will be created per application or family of applications. + +If the translator reaches an untranslated phrase that is the same as a +source phrase in the phrase book, \e {Qt Linguist} will show the +phrase book entry in the \e {Relevant phrases} panel at the bottom +right of the main window. Phrases which have translations that conflict +with those given in the phrase book are marked with a question mark in +the source text pane. Phrase Books are used to provide a common set of +translations to help ensure consistency. They can also be used to avoid +duplication of effort since the translations for a family of +applications can be produced once in the phrase book and the phrase book +used for the majority of translations in each application. + +Before a phrase book can be edited it must be created or if it already +exists, opened. Create a new phrase book by selecting +\Menu {Phrase|New Phrase Book} from the menu bar. You must enter a +filename and may change the location of the file if you wish. A newly +created phrase book is automatically opened. Open an existing phrase +book by choosing \Menu {Phrase|Open Phrase Book} from the menu bar. + +To add a new phrase click the \Button {New Phrase} button (or press +Alt+N) and type in a new source phrase. Press Tab and type in the +translation. Optionally press Tab and enter a definition -- this is +useful to distinguish different translations of the same source phrase. +This process may be repeated as often as necessary. + +You can delete a phrase by selecting it in the phrases list and clicking +Remove Phrase. + +Click the \e Save button (press Alt+S) and then click the \e Close +button (press Esc) once you've finished adding (and removing) phrases. + +When a phrase or set of phrases appears in the phrase book double +clicking the retquired target phrase will copy it to the translation +pane at the text cursor position. If you want to \e replace the text +in the translation pane with the target phrase, click the translation +pane, choose \Menu {Edit|Select All} (press \Key Alt+A) and then +double click the target phrase. + +\section1 Validation + +\index Validation of Translations +\index Accelerators!Validation +\index Punctuation!Validation +\index Phrases!Validation + +\e {Qt Linguist} provides three kinds of validation on translated +phrases. + +\list 1 +\i \e {Accelerator validation} detects translated phrases +that do not have an ampersand when the source phrase does and vice +versa. +\i \e {Punctuation validation} detects differences in the +terminating punctuation between source and translated phrases when this +may be significant, e.g. warns if the source phrase ends with an +ellipsis, exclamation mark or question mark, and the translated phrase +doesn't and vice versa. +\i \e {Phrases validation} detects source phrases that are +also in the phrase book but whose translation differs from that given in +the phrase book. +\endlist + +Validation may be switched on or off from the menu bar's Validation item +or using the toolbar buttons. Phrases that fail validation are marked +with a question mark in the source text pane. If you switch validation +off and then switch it on later, \e{Qt Linguist} will recheck all +phrases and mark any that fail validation. + +If any phrase in a context is invalid then the context itself will be +marked with a question mark; if all the phrases in a context are done +and are valid the context will be marked with a tick. + +Note that only phrases which are marked as done (with a tick) will +appear in the application. Invalid phrases and phrases which are +translated but not marked as done are kept in the translation source +file but are not used by the application. + +\section1 Qt Linguist Reference + +\section2 File Types + +\e {Qt Linguist} makes use of three kinds of file: + +\index .ts Files +\index Translation Source Files +\index .qm Files +\index Qt Message Files +\index .qph Files +\index Qt Phrase Book Files + +\list +\i \c .ts \e {translation source files} \BR are human-readable XML +files containing source phrases and their translations. These files are +usually created and updated by \l lupdate and are specific to an +application. +\i \c .qm \e {Qt message files} \BR are binary files that contain +translations used by an application at runtime. These files are +generated by \l lrelease, but can also be generated by \e {Qt +Linguist}. +\i \c .qph \e {Qt phrase book files} \BR are human-readable XML +files containing standard phrases and their translations. These files +are created and updated by \e {Qt Linguist} and may be used by any +number of projects and applications. +\endlist + +\section2 The Menu Bar + +\img menubar.png +\caption Menu Bar + +\list +\i \e {File} + \list + \i \e {Open... Ctrl+O} \BR pops up an open file dialog from which a + translation source \c .ts file can be chosen. + \i \e {Save Ctrl+S} \BR saves the current translation source \c .ts file. + \i \e {Save As...} \BR pops up a save as file dialog so that the + current translation source \c .ts file may be saved with a different + name and/or put in a different location. + \i \e {Release...} \BR pops up a save as file dialog. The + filename entered will be a Qt message \c .qm file of the translation + based on the current translation source file. The release manager's + command line tool \l lrelease performs the same function on + \e all of an application's translation source files. + \i \e {Print... Ctrl+P} \BR pops up a print dialog. If you click + OK the translation source and the translations will be printed. + \i \e {Recently opened files} \BR shows the \c .ts files that + have been opened recently, click one to open it. + \i \e {Exit Ctrl+Q} \BR closes \e {Qt Linguist}. + \endlist + +\i \e {Edit} + \list + \i \e {Undo Ctrl+Z} \BR undoes the last editing action in the + translation pane. + \i \e {Redo Ctrl+Y} \BR redoes the last editing action in the + translation pane. + \i \e {Cut Ctrl+X} \BR deletes any highlighted text in the + translation pane and saves a copy to the clipboard. + \i \e {Copy Ctrl+C} \BR copies the highlighted text in the + translation pane to the clipboard. + \i \e {Paste Ctrl+V} \BR pastes the clipboard text into the + translation pane. +\omit + \i \e {Delete} \BR deletes the highlighted text in the + translation pane. +\endomit + \i \e {Select All Ctrl+A} \BR selects all the text in the + translation pane ready for copying or deleting. + \i \e {Find... Ctrl+F} \BR pops up the + \link {The Find Dialog} Find dialog \endlink. When the dialog pops up + enter the text to be found and click the \e {Find Next} button. + Source phrases, translations and comments may be searched. + \i \e {Find Next F3} \BR finds the next occurrence of the text that + was last entered in the Find dialog. + \endlist + +\i \e {Translation} + \list + \i \e {Prev Unfinished Ctrl+K} \BR moves to the nearest previous + unfinished source phrase (unfinished means untranslated or + translated but failed validation). + \i \e {Next Unfinished Ctrl+L} \BR moves to the next unfinished source + phrase. + \i \e {Prev Shift+Ctrl+K} \BR moves to the previous source phrase. + \i \e {Next Shift+Ctrl+L} \BR moves to the next source phrase. + \i \e {Done \& NextCtrl+Enter} \BR mark this phrase as 'done' + (translated) and move to the next unfinished source phrase. + \i \e {Begin from Source Ctrl+B} \BR copies the source text into + the translation. + \endlist + +\i \e {Validation} (See the \l Validation section) + \list + \i \e {Accelerators} \BR toggles validation on or off for Alt + accelerators. + \i \e {Ending Punctuation} \BR switches validation on or off + for phrase ending punctuation, e.g. ellipsis, exclamation mark, + question mark, etc. + \i \e {Phrase Matches} \BR sets validation on or off for + matching against translations that are in the current phrase book. + \endlist + +\i \e {Phrase} (See the section \l {Creating ... Phrase +Books} for details.) + \list + \i \e {New Phrase Book... Ctrl+N} \BR pops up a save as file dialog. + You must enter a filename to be used for the phrase book and save + the file. Once saved you should open the phrase book to begin using + it. + \i \e {Open Phrase Book... Ctrl+H} \BR pops up an open file dialog. + Find and choose a phrase book to open. + \i \e {Close Phrase Book} \BR closes the current phrase book. + This will stop any further phrase validation taking place. + The same effect can be achieved by switching off phrase validation + using the Validation menu or the phrase toolbar button. + \i \e {Edit Phrase Book...} \BR pops up the + \link {The Phrase Dialog} phrase book dialog \endlink where you can + add, edit or delete phrases. + \i \e {Print Phrase Book...} \BR pops up a print dialog. If + you click OK the phrase book will be printed. + \endlist + +\i \e {View} + \list + \i \e {Revert Sorting} \BR puts the phrases in the source text + pane into their original order. + \i \e {Display Guesses} \BR turns the display of phrases and + guesses on or off. + \i \e {Statistics} \BR toggles the visibility of the Statistics dialog. + \i \e {Views} \BR toggles the visibility of the Context, Source text and + Phrase views. + \i \e {Toolbars} \BR toggles the visibility of the different toolbars. +\omit + \i \e {Large Icons} \BR switches between large or standard + size icons on the toolbar. + \i \e {Text Labels} \BR toggles the use of text labels on the + toolbar icons. +\endomit + \endlist + +\endlist + +\section2 The Toolbar + +\img toolbar.png +\caption Toolbar + +\list +\i \img fileopen.png +\BR +Pops up the open file dialog to open a new translation source \c .ts +file. + +\i \img filesave.png +\BR +Saves the current translation source \c .ts file. + +\i \img fileprint.png +\BR +Prints the current translation source \c .ts file. + +\i \img phrasebookopen.png +\BR +Pops up the file open dialog to open a new phrase book \c .qph file. + +\i \img editundo.png +\BR +Undoes the last editing action in the translation pane. + +\i \img editredo.png +\BR +Redoes the last editing action in the translation pane. + +\i \img editcut.png +\BR +Deletes any highlighted text in the translation pane and save a copy to +the clipboard. + +\i \img editcopy.png +\BR +Copies the highlighted text in the translation pane to the clipboard. + +\i \img editpaste.png +\BR +Pastes the clipboard text into the translation pane. + +\i \img editfind.png +\BR +Pops up the \link {The Find Dialog} Find dialog \endlink. + +\i \img prev.png +\BR +Moves to the previous source phrase. + +\i \img next.png +\BR +Moves to the next source phrase. + +\i \img prevunfinished.png +\BR +Moves to the previous unfinished source phrase. + +\i \img nextunfinished.png +\BR +Moves to the next unfinished source phrase. + +\i \img doneandnext.png +\BR +Marks the phrase as 'done' (translated) and move to the next +unfinished source phrase. + +\i \img validateaccelerators.png +\BR +Toggles accelerator validation on and off. + +\i \img validatepunctuation.png +\BR +Toggles phrase ending punctuation validation on and off. + +\i \img validatephrases.png +\BR +Toggles phrase book validation on or off. +\endlist + +\section2 The Find Dialog + +\img finddialog.png +\caption The Find Dialog + +Choose \Menu Edit|Find from the menu bar or press \Key Ctrl+F to pop +up the Find dialog. Press \Key F3 to repeat the last search. By +default the source phrases, translations and comments will all be +searched and the search will be case-insensitive. These settings can +be changed by checking or unchecking the checkboxes to reflect your +preferences. + +\section2 The Phrase Dialog + +This dialog is explained in the \l {Creating and Using Phrase Books} +section. diff --git a/tools/linguist/linguist.pro b/tools/linguist/linguist.pro new file mode 100644 index 000000000..3f1f28642 --- /dev/null +++ b/tools/linguist/linguist.pro @@ -0,0 +1,11 @@ +TEMPLATE = subdirs +SUBDIRS = linguist \ + tutorial/tt1 \ + tutorial/tt2 \ + tutorial/tt3 \ + lrelease \ + lupdate \ + qm2ts +CONFIG += ordered + +REQUIRES=full-config nocrosscompiler diff --git a/tools/linguist/linguist/about.ui b/tools/linguist/linguist/about.ui new file mode 100644 index 000000000..ba3f31b15 --- /dev/null +++ b/tools/linguist/linguist/about.ui @@ -0,0 +1,223 @@ + +AboutDialog +********************************************************************* +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +********************************************************************* + + + AboutDialog + + + + 0 + 0 + 484 + 640 + + + + TQt Linguist + + + + unnamed + + + 11 + + + 6 + + + + PixmapLabel1 + + + NoFrame + + + Plain + + + splash.png + + + false + + + AlignCenter + + + + + + + versionLabel + + + AlignCenter + + + + + + + TextLabel1_2 + + + Copyright (C) 2000-2008 Trolltech ASA. All Rights Reserved. + + + AlignCenter + + + + + + + TextLabel1_3 + + + + 1 + 0 + 0 + 0 + + + + <p>TQt Commercial Edition license holders: This program is licensed to you under the terms of the TQt Commercial License Agreement. For details, see the file LICENSE that came with this software distribution.</p><p></p><p>TQt Open Source Edition users: This program is licensed to you under the terms of the GNU General Public License Version 2. For details, see the file LICENSE.GPL that came with this software distribution.</p><p>The program is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.</p> + + + WordBreak|AlignVCenter|AlignLeft + + + + + + + Spacer3 + + + Vertical + + + Expanding + + + + 20 + 20 + + + + + + Layout1 + + + + unnamed + + + 0 + + + 6 + + + + Spacer2 + + + Horizontal + + + Expanding + + + + 20 + 20 + + + + + + PushButton1 + + + OK + + + true + + + true + + + + + Spacer1 + + + Horizontal + + + Expanding + + + + 20 + 20 + + + + + + + + + + PushButton1 + clicked() + AboutDialog + accept() + + + + init() + destroy() + + + + diff --git a/tools/linguist/linguist/finddialog.cpp b/tools/linguist/linguist/finddialog.cpp new file mode 100644 index 000000000..979915aa9 --- /dev/null +++ b/tools/linguist/linguist/finddialog.cpp @@ -0,0 +1,183 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +/* TRANSLATOR FindDialog + + Choose Edit|Find from the menu bar or press Ctrl+F to pop up the + Find dialog +*/ + +#include "finddialog.h" + +#include +#include +#include +#include +#include +#include + +FindDialog::FindDialog( bool replace, TQWidget *parent, const char *name, + bool modal ) + : TQDialog( parent, name, modal ) +{ + sourceText = 0; + + led = new TQLineEdit( this, "find line edit" ); + TQLabel *findWhat = new TQLabel( led, tr("Fi&nd what:"), this, "find what" ); + TQLabel *replaceWith = 0; + TQPushButton *findNxt = new TQPushButton( tr("&Find Next"), this, + "find next" ); + findNxt->setDefault( TRUE ); + connect( findNxt, SIGNAL(clicked()), this, SLOT(emitFindNext()) ); + TQPushButton *cancel = new TQPushButton( tr("Cancel"), this, "cancel find" ); + connect( cancel, SIGNAL(clicked()), this, SLOT(reject()) ); + + TQVBoxLayout *bl = new TQVBoxLayout( 6, "find button layout" ); + bl->addWidget( findNxt ); + + matchCase = new TQCheckBox( tr("&Match case"), this, "find match case" ); + matchCase->setChecked( FALSE ); + + if ( replace ) { + TQWhatsThis::add( this, tr("This window allows you to search and replace" + " some text in the translations.") ); + + red = new TQLineEdit( this, "replace line edit" ); + replaceWith = new TQLabel( red, tr("Replace &with:"), this, + "replace with" ); + setTabOrder( led, red ); + + TQPushButton *replace = new TQPushButton( tr("&Replace"), this, + "replace" ); + connect( replace, SIGNAL(clicked()), this, SLOT(emitReplace()) ); + TQPushButton *replaceAll = new TQPushButton( tr("Replace &All"), this, + "replace all" ); + connect( replaceAll, SIGNAL(clicked()), this, SLOT(emitReplaceAll()) ); + setTabOrder( findNxt, replace ); + setTabOrder( replace, replaceAll ); + setTabOrder( replaceAll, cancel ); + + TQWhatsThis::add( replace, tr("Click here to replace the next occurrence" + " of the text you typed in.") ); + TQWhatsThis::add( replaceAll, tr("Click here to replace all occurrences" + " of the text you typed in.") ); + + bl->addWidget( replace ); + bl->addWidget( replaceAll ); + + TQGridLayout *gl = new TQGridLayout( this, 4, 3, 11, 11, + "find outer layout" ); + gl->addWidget( findWhat, 0, 0 ); + gl->addWidget( led, 0, 1 ); + gl->addWidget( replaceWith, 1, 0 ); + gl->addWidget( red, 1, 1 ); + gl->addMultiCellWidget( matchCase, 2, 2, 0, 1 ); + gl->addMultiCell( bl, 0, 3, 3, 3 ); + } else { + TQWhatsThis::add( this, tr("This window allows you to search for some" + " text in the translation source file.") ); + + sourceText = new TQCheckBox( tr("&Source texts"), this, + "find in source texts" ); + sourceText->setChecked( TRUE ); + translations = new TQCheckBox( tr("&Translations"), this, + "find in translations" ); + translations->setChecked( TRUE ); + comments = new TQCheckBox( tr("&Comments"), this, "find in comments" ); + comments->setChecked( TRUE ); + + TQWhatsThis::add( sourceText, tr("Source texts are searched when" + " checked.") ); + TQWhatsThis::add( translations, tr("Translations are searched when" + " checked.") ); + TQWhatsThis::add( comments, tr("Comments and contexts are searched when" + " checked.") ); + + TQVBoxLayout *cl = new TQVBoxLayout( 6, "find checkbox layout" ); + + TQGridLayout *gl = new TQGridLayout( this, 3, 4, 11, 11, + "find outer layout" ); + gl->addWidget( findWhat, 0, 0 ); + gl->addMultiCellWidget( led, 0, 0, 1, 2 ); + gl->addWidget( matchCase, 1, 2 ); + gl->addMultiCell( bl, 0, 2, 3, 3 ); + gl->addMultiCell( cl, 1, 2, 0, 1 ); + gl->setColStretch( 0, 0 ); + gl->addColSpacing( 1, 40 ); + gl->setColStretch( 2, 1 ); + gl->setColStretch( 3, 0 ); + + cl->addWidget( sourceText ); + cl->addWidget( translations ); + cl->addWidget( comments ); + cl->addStretch( 1 ); + } + + TQWhatsThis::add( led, tr("Type in the text to search for.") ); + + TQWhatsThis::add( matchCase, tr("Texts such as 'TeX' and 'tex' are" + " considered as different when checked.") ); + TQWhatsThis::add( findNxt, tr("Click here to find the next occurrence of the" + " text you typed in.") ); + TQWhatsThis::add( cancel, tr("Click here to close this window.") ); + + bl->addWidget( cancel ); + bl->addStretch( 1 ); + + resize( 400, 1 ); + setMaximumHeight( height() ); + + led->setFocus(); +} + +void FindDialog::emitFindNext() +{ + int where; + if ( sourceText != 0 ) + where = ( sourceText->isChecked() ? SourceText : 0 ) | + ( translations->isChecked() ? Translations : 0 ) | + ( comments->isChecked() ? Comments : 0 ); + else + where = Translations; + emit findNext( led->text(), where, matchCase->isChecked() ); +} + +void FindDialog::emitReplace() +{ + emit replace( led->text(), red->text(), matchCase->isChecked(), FALSE ); +} + +void FindDialog::emitReplaceAll() +{ + emit replace( led->text(), red->text(), matchCase->isChecked(), TRUE ); +} diff --git a/tools/linguist/linguist/finddialog.h b/tools/linguist/linguist/finddialog.h new file mode 100644 index 000000000..0a9a3554d --- /dev/null +++ b/tools/linguist/linguist/finddialog.h @@ -0,0 +1,68 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef FINDDIALOG_H +#define FINDDIALOG_H + +#include + +class TQCheckBox; +class TQLineEdit; + +class FindDialog : public TQDialog +{ + Q_OBJECT +public: + enum { SourceText = 0x1, Translations = 0x2, Comments = 0x4 }; + + FindDialog( bool replace, TQWidget *parent = 0, const char *name = 0, bool modal = FALSE ); + +signals: + void findNext( const TQString& text, int where, bool matchCase ); + void replace( const TQString& before, const TQString& after, bool matchCase, bool all ); + +private slots: + void emitFindNext(); + void emitReplace(); + void emitReplaceAll(); + +private: + TQLineEdit *led; + TQLineEdit *red; + TQCheckBox *sourceText; + TQCheckBox *translations; + TQCheckBox *comments; + TQCheckBox *matchCase; +}; + +#endif diff --git a/tools/linguist/linguist/images/accelerator.png b/tools/linguist/linguist/images/accelerator.png new file mode 100644 index 000000000..173adb4f8 Binary files /dev/null and b/tools/linguist/linguist/images/accelerator.png differ diff --git a/tools/linguist/linguist/images/appicon.png b/tools/linguist/linguist/images/appicon.png new file mode 100644 index 000000000..90e143b65 Binary files /dev/null and b/tools/linguist/linguist/images/appicon.png differ diff --git a/tools/linguist/linguist/images/book.png b/tools/linguist/linguist/images/book.png new file mode 100644 index 000000000..dd850abb0 Binary files /dev/null and b/tools/linguist/linguist/images/book.png differ diff --git a/tools/linguist/linguist/images/d_accelerator.png b/tools/linguist/linguist/images/d_accelerator.png new file mode 100644 index 000000000..eaa2be614 Binary files /dev/null and b/tools/linguist/linguist/images/d_accelerator.png differ diff --git a/tools/linguist/linguist/images/d_book.png b/tools/linguist/linguist/images/d_book.png new file mode 100644 index 000000000..b61d61172 Binary files /dev/null and b/tools/linguist/linguist/images/d_book.png differ diff --git a/tools/linguist/linguist/images/d_doneandnext.png b/tools/linguist/linguist/images/d_doneandnext.png new file mode 100644 index 000000000..e3a3fe107 Binary files /dev/null and b/tools/linguist/linguist/images/d_doneandnext.png differ diff --git a/tools/linguist/linguist/images/d_editcopy.png b/tools/linguist/linguist/images/d_editcopy.png new file mode 100644 index 000000000..578b59112 Binary files /dev/null and b/tools/linguist/linguist/images/d_editcopy.png differ diff --git a/tools/linguist/linguist/images/d_editcut.png b/tools/linguist/linguist/images/d_editcut.png new file mode 100644 index 000000000..8d50ae0a0 Binary files /dev/null and b/tools/linguist/linguist/images/d_editcut.png differ diff --git a/tools/linguist/linguist/images/d_editpaste.png b/tools/linguist/linguist/images/d_editpaste.png new file mode 100644 index 000000000..78cab1048 Binary files /dev/null and b/tools/linguist/linguist/images/d_editpaste.png differ diff --git a/tools/linguist/linguist/images/d_fileopen.png b/tools/linguist/linguist/images/d_fileopen.png new file mode 100644 index 000000000..ddbd33d98 Binary files /dev/null and b/tools/linguist/linguist/images/d_fileopen.png differ diff --git a/tools/linguist/linguist/images/d_filesave.png b/tools/linguist/linguist/images/d_filesave.png new file mode 100644 index 000000000..5d1476d28 Binary files /dev/null and b/tools/linguist/linguist/images/d_filesave.png differ diff --git a/tools/linguist/linguist/images/d_next.png b/tools/linguist/linguist/images/d_next.png new file mode 100644 index 000000000..f455e1fdb Binary files /dev/null and b/tools/linguist/linguist/images/d_next.png differ diff --git a/tools/linguist/linguist/images/d_nextunfinished.png b/tools/linguist/linguist/images/d_nextunfinished.png new file mode 100644 index 000000000..c2b06ecaf Binary files /dev/null and b/tools/linguist/linguist/images/d_nextunfinished.png differ diff --git a/tools/linguist/linguist/images/d_phrase.png b/tools/linguist/linguist/images/d_phrase.png new file mode 100644 index 000000000..acdd2535e Binary files /dev/null and b/tools/linguist/linguist/images/d_phrase.png differ diff --git a/tools/linguist/linguist/images/d_prev.png b/tools/linguist/linguist/images/d_prev.png new file mode 100644 index 000000000..a68fe54fa Binary files /dev/null and b/tools/linguist/linguist/images/d_prev.png differ diff --git a/tools/linguist/linguist/images/d_prevunfinished.png b/tools/linguist/linguist/images/d_prevunfinished.png new file mode 100644 index 000000000..ce956a7b5 Binary files /dev/null and b/tools/linguist/linguist/images/d_prevunfinished.png differ diff --git a/tools/linguist/linguist/images/d_print.png b/tools/linguist/linguist/images/d_print.png new file mode 100644 index 000000000..b2791a7b5 Binary files /dev/null and b/tools/linguist/linguist/images/d_print.png differ diff --git a/tools/linguist/linguist/images/d_punctuation.png b/tools/linguist/linguist/images/d_punctuation.png new file mode 100644 index 000000000..8eebab8bf Binary files /dev/null and b/tools/linguist/linguist/images/d_punctuation.png differ diff --git a/tools/linguist/linguist/images/d_redo.png b/tools/linguist/linguist/images/d_redo.png new file mode 100644 index 000000000..6e993cc67 Binary files /dev/null and b/tools/linguist/linguist/images/d_redo.png differ diff --git a/tools/linguist/linguist/images/d_s_check_danger.png b/tools/linguist/linguist/images/d_s_check_danger.png new file mode 100644 index 000000000..3fadeb146 Binary files /dev/null and b/tools/linguist/linguist/images/d_s_check_danger.png differ diff --git a/tools/linguist/linguist/images/d_s_check_obs.png b/tools/linguist/linguist/images/d_s_check_obs.png new file mode 100644 index 000000000..4836e2ffd Binary files /dev/null and b/tools/linguist/linguist/images/d_s_check_obs.png differ diff --git a/tools/linguist/linguist/images/d_s_check_off.png b/tools/linguist/linguist/images/d_s_check_off.png new file mode 100644 index 000000000..58f7fb667 Binary files /dev/null and b/tools/linguist/linguist/images/d_s_check_off.png differ diff --git a/tools/linguist/linguist/images/d_s_check_on.png b/tools/linguist/linguist/images/d_s_check_on.png new file mode 100644 index 000000000..4836e2ffd Binary files /dev/null and b/tools/linguist/linguist/images/d_s_check_on.png differ diff --git a/tools/linguist/linguist/images/d_searchfind.png b/tools/linguist/linguist/images/d_searchfind.png new file mode 100644 index 000000000..e85e33fe0 Binary files /dev/null and b/tools/linguist/linguist/images/d_searchfind.png differ diff --git a/tools/linguist/linguist/images/d_undo.png b/tools/linguist/linguist/images/d_undo.png new file mode 100644 index 000000000..22ac97f27 Binary files /dev/null and b/tools/linguist/linguist/images/d_undo.png differ diff --git a/tools/linguist/linguist/images/doneandnext.png b/tools/linguist/linguist/images/doneandnext.png new file mode 100644 index 000000000..1cf8888ec Binary files /dev/null and b/tools/linguist/linguist/images/doneandnext.png differ diff --git a/tools/linguist/linguist/images/editcopy.png b/tools/linguist/linguist/images/editcopy.png new file mode 100644 index 000000000..804c98ce5 Binary files /dev/null and b/tools/linguist/linguist/images/editcopy.png differ diff --git a/tools/linguist/linguist/images/editcut.png b/tools/linguist/linguist/images/editcut.png new file mode 100644 index 000000000..a911482df Binary files /dev/null and b/tools/linguist/linguist/images/editcut.png differ diff --git a/tools/linguist/linguist/images/editpaste.png b/tools/linguist/linguist/images/editpaste.png new file mode 100644 index 000000000..193814121 Binary files /dev/null and b/tools/linguist/linguist/images/editpaste.png differ diff --git a/tools/linguist/linguist/images/fileopen.png b/tools/linguist/linguist/images/fileopen.png new file mode 100644 index 000000000..300529013 Binary files /dev/null and b/tools/linguist/linguist/images/fileopen.png differ diff --git a/tools/linguist/linguist/images/filesave.png b/tools/linguist/linguist/images/filesave.png new file mode 100644 index 000000000..c137165b0 Binary files /dev/null and b/tools/linguist/linguist/images/filesave.png differ diff --git a/tools/linguist/linguist/images/next.png b/tools/linguist/linguist/images/next.png new file mode 100644 index 000000000..4b29ff454 Binary files /dev/null and b/tools/linguist/linguist/images/next.png differ diff --git a/tools/linguist/linguist/images/nextunfinished.png b/tools/linguist/linguist/images/nextunfinished.png new file mode 100644 index 000000000..9892b6580 Binary files /dev/null and b/tools/linguist/linguist/images/nextunfinished.png differ diff --git a/tools/linguist/linguist/images/pagecurl.png b/tools/linguist/linguist/images/pagecurl.png new file mode 100644 index 000000000..2d3f2ff8e Binary files /dev/null and b/tools/linguist/linguist/images/pagecurl.png differ diff --git a/tools/linguist/linguist/images/phrase.png b/tools/linguist/linguist/images/phrase.png new file mode 100644 index 000000000..d7dfcb5bf Binary files /dev/null and b/tools/linguist/linguist/images/phrase.png differ diff --git a/tools/linguist/linguist/images/prev.png b/tools/linguist/linguist/images/prev.png new file mode 100644 index 000000000..4e3556c8d Binary files /dev/null and b/tools/linguist/linguist/images/prev.png differ diff --git a/tools/linguist/linguist/images/prevunfinished.png b/tools/linguist/linguist/images/prevunfinished.png new file mode 100644 index 000000000..a3bed548b Binary files /dev/null and b/tools/linguist/linguist/images/prevunfinished.png differ diff --git a/tools/linguist/linguist/images/print.png b/tools/linguist/linguist/images/print.png new file mode 100644 index 000000000..cc083edf7 Binary files /dev/null and b/tools/linguist/linguist/images/print.png differ diff --git a/tools/linguist/linguist/images/punctuation.png b/tools/linguist/linguist/images/punctuation.png new file mode 100644 index 000000000..849d4a9a0 Binary files /dev/null and b/tools/linguist/linguist/images/punctuation.png differ diff --git a/tools/linguist/linguist/images/redo.png b/tools/linguist/linguist/images/redo.png new file mode 100644 index 000000000..abdad26c9 Binary files /dev/null and b/tools/linguist/linguist/images/redo.png differ diff --git a/tools/linguist/linguist/images/s_check_danger.png b/tools/linguist/linguist/images/s_check_danger.png new file mode 100644 index 000000000..700530438 Binary files /dev/null and b/tools/linguist/linguist/images/s_check_danger.png differ diff --git a/tools/linguist/linguist/images/s_check_obs.png b/tools/linguist/linguist/images/s_check_obs.png new file mode 100644 index 000000000..b171b2ab8 Binary files /dev/null and b/tools/linguist/linguist/images/s_check_obs.png differ diff --git a/tools/linguist/linguist/images/s_check_off.png b/tools/linguist/linguist/images/s_check_off.png new file mode 100644 index 000000000..cf45bc090 Binary files /dev/null and b/tools/linguist/linguist/images/s_check_off.png differ diff --git a/tools/linguist/linguist/images/s_check_on.png b/tools/linguist/linguist/images/s_check_on.png new file mode 100644 index 000000000..b5238f768 Binary files /dev/null and b/tools/linguist/linguist/images/s_check_on.png differ diff --git a/tools/linguist/linguist/images/searchfind.png b/tools/linguist/linguist/images/searchfind.png new file mode 100644 index 000000000..3f369fdb3 Binary files /dev/null and b/tools/linguist/linguist/images/searchfind.png differ diff --git a/tools/linguist/linguist/images/splash.png b/tools/linguist/linguist/images/splash.png new file mode 100644 index 000000000..8e807185d Binary files /dev/null and b/tools/linguist/linguist/images/splash.png differ diff --git a/tools/linguist/linguist/images/undo.png b/tools/linguist/linguist/images/undo.png new file mode 100644 index 000000000..839a823f6 Binary files /dev/null and b/tools/linguist/linguist/images/undo.png differ diff --git a/tools/linguist/linguist/images/whatsthis.xpm b/tools/linguist/linguist/images/whatsthis.xpm new file mode 100644 index 000000000..e45dc2668 --- /dev/null +++ b/tools/linguist/linguist/images/whatsthis.xpm @@ -0,0 +1,24 @@ +/* XPM */ +static char *magick[] = { +/* columns rows colors chars-per-pixel */ +"16 16 3 1", +" c None", +"o c #000000000000", +"a c #000000008000", +/* pixels */ +"o aaaaa ", +"oo aaa aaa ", +"ooo aaa aaa", +"oooo aa aa", +"ooooo aa aa", +"oooooo a aaa", +"ooooooo aaa ", +"oooooooo aaa ", +"ooooooooo aaa ", +"ooooo aaa ", +"oo ooo ", +"o ooo aaa ", +" ooo aaa ", +" ooo ", +" ooo ", +" ooo "}; diff --git a/tools/linguist/linguist/linguist.icns b/tools/linguist/linguist/linguist.icns new file mode 100644 index 000000000..f51565ecc Binary files /dev/null and b/tools/linguist/linguist/linguist.icns differ diff --git a/tools/linguist/linguist/linguist.ico b/tools/linguist/linguist/linguist.ico new file mode 100644 index 000000000..2816c7cc2 Binary files /dev/null and b/tools/linguist/linguist/linguist.ico differ diff --git a/tools/linguist/linguist/linguist.pro b/tools/linguist/linguist/linguist.pro new file mode 100644 index 000000000..da4d782df --- /dev/null +++ b/tools/linguist/linguist/linguist.pro @@ -0,0 +1,109 @@ +TEMPLATE = app +LANGUAGE = C++ +CONFIG += qt warn_on + + +SOURCES += finddialog.cpp \ + main.cpp \ + msgedit.cpp \ + phrase.cpp \ + phrasebookbox.cpp \ + phraselv.cpp \ + printout.cpp \ + simtexth.cpp \ + trwindow.cpp \ + listviews.cpp \ + ../shared/metatranslator.cpp +HEADERS += finddialog.h \ + msgedit.h \ + phrase.h \ + phrasebookbox.h \ + phraselv.h \ + printout.h \ + trwindow.h \ + listviews.h \ + ../shared/metatranslator.h + + +TRANSLATIONS = linguist_de.ts \ + linguist_fr.ts + +DEFINES += QT_INTERNAL_XML +include( ../../../src/qt_professional.pri ) + +DESTDIR = ../../../bin +TARGET = linguist + + +LIBS += -L$$QT_BUILD_TREE/lib -lqassistantclient + +win32:RC_FILE = linguist.rc + +mac { + staticlib:CONFIG -= global_init_link_order #yuck + RC_FILE = linguist.icns +} + +PROJECTNAME = Qt Linguist + +target.path=$$bins.path +INSTALLS += target + +linguisttranslations.files = *.qm +linguisttranslations.path = $$translations.path +INSTALLS += linguisttranslations + +phrasebooks.path=$$data.path/phrasebooks +phrasebooks.files = ../phrasebooks/* +INSTALLS += phrasebooks +FORMS = about.ui \ + statistics.ui +IMAGES = images/accelerator.png \ + images/book.png \ + images/s_check_danger.png \ + images/s_check_obs.png \ + images/s_check_off.png \ + images/s_check_on.png \ + images/d_s_check_danger.png \ + images/d_s_check_obs.png \ + images/d_s_check_off.png \ + images/d_s_check_on.png \ + images/d_accelerator.png \ + images/d_book.png \ + images/d_doneandnext.png \ + images/d_editcopy.png \ + images/d_editcut.png \ + images/d_editpaste.png \ + images/d_fileopen.png \ + images/d_filesave.png \ + images/d_next.png \ + images/d_nextunfinished.png \ + images/d_prev.png \ + images/d_prevunfinished.png \ + images/d_phrase.png \ + images/d_print.png \ + images/d_punctuation.png \ + images/d_redo.png \ + images/d_searchfind.png \ + images/d_undo.png \ + images/doneandnext.png \ + images/editcopy.png \ + images/editcut.png \ + images/editpaste.png \ + images/punctuation.png \ + images/fileopen.png \ + images/filesave.png \ + images/appicon.png \ + images/next.png \ + images/nextunfinished.png \ + images/pagecurl.png \ + images/phrase.png \ + images/prev.png \ + images/prevunfinished.png \ + images/print.png \ + images/redo.png \ + images/searchfind.png \ + images/splash.png \ + images/undo.png \ + images/whatsthis.xpm +INCLUDEPATH += ../shared diff --git a/tools/linguist/linguist/linguist.rc b/tools/linguist/linguist/linguist.rc new file mode 100644 index 000000000..865e021c4 --- /dev/null +++ b/tools/linguist/linguist/linguist.rc @@ -0,0 +1 @@ +IDI_ICON1 ICON DISCARDABLE "linguist.ico" diff --git a/tools/linguist/linguist/linguist_de.ts b/tools/linguist/linguist/linguist_de.ts new file mode 100644 index 000000000..06d818b57 --- /dev/null +++ b/tools/linguist/linguist/linguist_de.ts @@ -0,0 +1,993 @@ + + + AboutDialog + + Qt Linguist + + + + Copyright (C) 2000-2008 Trolltech ASA. All Rights Reserved. + + + + <p>This program is licensed to you under the terms of the GNU General Public License Version 2 as published by the Free Software Foundation. This gives you legal permission to copy, distribute and/or modify this software under certain conditions. For details, see the file 'LICENSE.GPL' that came with this software distribution. If you did not get the file, send email to info@trolltech.com.</p> +<p>The program is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.</p> + + + + OK + + + + + EditorPage + + Source text + + + + Translation + + + + + FindDialog + Choose Edit|Find from the menu bar or press Ctrl+F to pop up the Find dialog + + Fi&nd what: + + + + &Find Next + + + + Cancel + + + + &Match case + + + + This window allows you to search and replace some text in the translations. + + + + Replace &with: + + + + &Replace + + + + Replace &All + + + + Click here to replace the next occurrence of the text you typed in. + + + + Click here to replace all occurrences of the text you typed in. + + + + This window allows you to search for some text in the translation source file. + + + + &Source texts + + + + &Translations + + + + &Comments + + + + Source texts are searched when checked. + + + + Translations are searched when checked. + + + + Comments and contexts are searched when checked. + + + + Type in the text to search for. + + + + Texts such as 'TeX' and 'tex' are considered as different when checked. + + + + Click here to find the next occurrence of the text you typed in. + + + + Click here to close this window. + + + + + MessageEditor + + bell + + + + backspace + + + + new page + + + + new line + + + + carriage return + + + + tab + + + + Source text + + + + Done + + + + Translation + + + + Phrases + + + + Phrases and guesses: + + + + This whole panel allows you to view and edit the translation of some source text. + + + + This area shows the source text. + + + + This area shows a comment that may guide you, and the context in which the text occurs. + + + + This is where you can enter or modify the translation of some source text. + + + + Guess + + + + Guess (%1) + + + + + PageCurl + + Next unfinished phrase + + + + Previous unfinished phrase + + + + + PhraseBookBox + Go to Phrase > Edit Phrase Book... The dialog that pops up is a PhraseBookBox. + + S&ource phrase: + + + + &Translation: + + + + &Definition: + + + + &New Phrase + + + + &Remove Phrase + + + + &Save + + + + Close + + + + This window allows you to add, modify, or delete phrases in a phrase book. + + + + This is the phrase in the source language. + + + + This is the phrase in the target language corresponding to the source phrase. + + + + This is a definition for the source phrase. + + + + Click here to add the phrase to the phrase book. + + + + Click here to remove the phrase from the phrase book. + + + + Click here to save the changes made. + + + + Click here to close this window. + + + + Qt Linguist + + + + Cannot save phrase book '%1'. + + + + + PhraseLV + The phrase list in the right panel of the main window (with Source phrase, Target phrase, and Definition in its header) is a PhraseLV object. + + (New Phrase) + + + + This is a list of phrase entries relevant to the source text. Each phrase is supplemented with a suggested translation and a definition. + + + + <p><u>%1:</u>&nbsp;&nbsp;%2</p><p><u>%3:</u>&nbsp;&nbsp;%4</p><p><u>%5:</u>&nbsp;&nbsp;%6</p> + + + + Source phrase + + + + Translation + + + + Definition + + + + + QObject + + Qt Linguist + + + + + TrWindow + This is the application's main window. + + Context + + + + Done + + + + Items + + + + MOD + + + + Qt Linguist + + + + This panel lists the source contexts. + + + + This panel lists the source texts. Items that violate validation rules are marked with a warning. + + + + Loading... + + + + %1 source phrase(s) loaded. + + + + Cannot open '%1'. + + + + Qt translation source (*.ts) +All files (*) + + + + File saved. + + + + Cannot save '%1'. + + + + Qt message files for released applications (*.qm) +All files (*) + + + + Release + + + + File created. + + + + Printing... + + + + Context: %1 + + + + finished + + + + unresolved + + + + obsolete + + + + Printing... (page %1) + + + + Printing completed + + + + Printing aborted + + + + Search wrapped. + + + + Cannot find the string '%1'. + + + + Qt phrase books (*.qph) +All files (*) + + + + Create New Phrase Book + + + + A file called '%1' already exists. Please choose another name. + + + + Phrase book created. + + + + %1 phrase(s) loaded. + + + + %1 - %2 + + + + Do you want to save '%1'? + + + + Qt Linguist by Trolltech + + + + No phrase to translate. + + + + No untranslated phrases left. + + + + &File + + + + &Edit + + + + &Translation + + + + V&alidation + + + + &Phrases + + + + &View + + + + &Help + + + + &Open... + + + + Ctrl+O + + + + &Save + + + + Ctrl+S + + + + Save &As... + + + + &Release... + + + + &Print... + + + + Ctrl+P + + + + Re&cently opened files + + + + E&xit + + + + Ctrl+Q + + + + &Undo + + + + Ctrl+Z + + + + &Redo + + + + Ctrl+Y + + + + Cu&t + + + + Ctrl+X + + + + &Copy + + + + Ctrl+C + + + + &Paste + + + + Ctrl+V + + + + Select &All + + + + Ctrl+A + + + + &Find... + + + + Ctrl+F + + + + Find &Next + + + + &Replace... + + + + Ctrl+H + + + + &Prev Unfinished + + + + Ctrl+K + + + + &Next Unfinished + + + + Ctrl+L + + + + P&rev + + + + Ctrl+Shift+K + + + + Ne&xt + + + + Ctrl+Shift+L + + + + Done and &Next + + + + Ctrl+Enter + + + + Ctrl+Return + + + + &Begin from Source + + + + Ctrl+B + + + + &New Phrase Book... + + + + Ctrl+N + + + + &Open Phrase Book... + + + + &Close Phrase Book + + + + &Edit Phrase Book... + + + + &Print Phrase Book... + + + + &Accelerators + + + + &Ending Punctuation + + + + &Phrase Matches + + + + &Revert Sorting + + + + &Display guesses + + + + Vie&ws + + + + &Toolbars + + + + &Manual + + + + &About + + + + About &Qt + + + + &What's This? + + + + Open a Qt translation source file (TS file) for editing. + + + + Save changes made to this Qt translation source file. + + + + Save changes made to this Qt translationsource file into a new file. + + + + Create a Qt message file suitable for released applications from the current message file. + + + + Print a list of all the phrases in the current Qt translation source file. + + + + Close this window and exit. + + + + Undo the last editing operation performed on the translation. + + + + Redo an undone editing operation performed on the translation. + + + + Copy the selected translation text to the clipboard and deletes it. + + + + Copy the selected translation text to the clipboard. + + + + Paste the clipboard text into the translation. + + + + Select the whole translation text. + + + + Search for some text in the translation source file. + + + + Continue the search where it was left. + + + + Search for some text in the translation source file and replace it by another text. + + + + Create a new phrase book. + + + + Open a phrase book to assist translation. + + + + Toggle validity checks of accelerators. + + + + Toggle validity checks of ending punctuation. + + + + Toggle checking that phrase suggestions are used. + + + + Sort the items back in the same order as in the message file. + + + + Set whether or not to display translation guesses. + + + + Display the manual for %1. + + + + Display information about %1. + + + + Display information about the Qt toolkit by Trolltech. + + + + Enter What's This? mode. + + + + Copies the source text into the translation field. + + + + Moves to the next item. + + + + Moves to the previous item. + + + + Moves to the next unfinished item. + + + + Moves to the previous unfinished item. + + + + Marks this item as done and moves to the next unfinished item. + + + + File + + + + Edit + + + + Translation + + + + Validation + + + + Help + + + + Open + + + + Save + + + + Print + + + + Open Phrase Book + + + + Undo + + + + Redo + + + + Cut + + + + Copy + + + + Paste + + + + Find + + + + Replace + + + + Prev + + + + Next + + + + Prev Unfinished + + + + Next Unfinished + + + + Done and Next + + + + Accelerators + + + + Punctuation + + + + Phrases + + + + What's This? + + + + Cannot read from phrase book '%1'. + + + + Close this phrase book. + + + + Allow you to add, modify, or delete phrases of this phrase book. + + + + Print the entries of the phrase book. + + + + Cannot create phrase book '%1'. + + + + Accelerator possibly superfluous in translation. + + + + Accelerator possibly missing in translation. + + + + Translation does not end with the same punctuation as the source text. + + + + A phrase book suggestion for '%1' was ignored. + + + + ... + + + + Version %1 + + + + diff --git a/tools/linguist/linguist/linguist_fr.ts b/tools/linguist/linguist/linguist_fr.ts new file mode 100644 index 000000000..06d818b57 --- /dev/null +++ b/tools/linguist/linguist/linguist_fr.ts @@ -0,0 +1,993 @@ + + + AboutDialog + + Qt Linguist + + + + Copyright (C) 2000-2008 Trolltech ASA. All Rights Reserved. + + + + <p>This program is licensed to you under the terms of the GNU General Public License Version 2 as published by the Free Software Foundation. This gives you legal permission to copy, distribute and/or modify this software under certain conditions. For details, see the file 'LICENSE.GPL' that came with this software distribution. If you did not get the file, send email to info@trolltech.com.</p> +<p>The program is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.</p> + + + + OK + + + + + EditorPage + + Source text + + + + Translation + + + + + FindDialog + Choose Edit|Find from the menu bar or press Ctrl+F to pop up the Find dialog + + Fi&nd what: + + + + &Find Next + + + + Cancel + + + + &Match case + + + + This window allows you to search and replace some text in the translations. + + + + Replace &with: + + + + &Replace + + + + Replace &All + + + + Click here to replace the next occurrence of the text you typed in. + + + + Click here to replace all occurrences of the text you typed in. + + + + This window allows you to search for some text in the translation source file. + + + + &Source texts + + + + &Translations + + + + &Comments + + + + Source texts are searched when checked. + + + + Translations are searched when checked. + + + + Comments and contexts are searched when checked. + + + + Type in the text to search for. + + + + Texts such as 'TeX' and 'tex' are considered as different when checked. + + + + Click here to find the next occurrence of the text you typed in. + + + + Click here to close this window. + + + + + MessageEditor + + bell + + + + backspace + + + + new page + + + + new line + + + + carriage return + + + + tab + + + + Source text + + + + Done + + + + Translation + + + + Phrases + + + + Phrases and guesses: + + + + This whole panel allows you to view and edit the translation of some source text. + + + + This area shows the source text. + + + + This area shows a comment that may guide you, and the context in which the text occurs. + + + + This is where you can enter or modify the translation of some source text. + + + + Guess + + + + Guess (%1) + + + + + PageCurl + + Next unfinished phrase + + + + Previous unfinished phrase + + + + + PhraseBookBox + Go to Phrase > Edit Phrase Book... The dialog that pops up is a PhraseBookBox. + + S&ource phrase: + + + + &Translation: + + + + &Definition: + + + + &New Phrase + + + + &Remove Phrase + + + + &Save + + + + Close + + + + This window allows you to add, modify, or delete phrases in a phrase book. + + + + This is the phrase in the source language. + + + + This is the phrase in the target language corresponding to the source phrase. + + + + This is a definition for the source phrase. + + + + Click here to add the phrase to the phrase book. + + + + Click here to remove the phrase from the phrase book. + + + + Click here to save the changes made. + + + + Click here to close this window. + + + + Qt Linguist + + + + Cannot save phrase book '%1'. + + + + + PhraseLV + The phrase list in the right panel of the main window (with Source phrase, Target phrase, and Definition in its header) is a PhraseLV object. + + (New Phrase) + + + + This is a list of phrase entries relevant to the source text. Each phrase is supplemented with a suggested translation and a definition. + + + + <p><u>%1:</u>&nbsp;&nbsp;%2</p><p><u>%3:</u>&nbsp;&nbsp;%4</p><p><u>%5:</u>&nbsp;&nbsp;%6</p> + + + + Source phrase + + + + Translation + + + + Definition + + + + + QObject + + Qt Linguist + + + + + TrWindow + This is the application's main window. + + Context + + + + Done + + + + Items + + + + MOD + + + + Qt Linguist + + + + This panel lists the source contexts. + + + + This panel lists the source texts. Items that violate validation rules are marked with a warning. + + + + Loading... + + + + %1 source phrase(s) loaded. + + + + Cannot open '%1'. + + + + Qt translation source (*.ts) +All files (*) + + + + File saved. + + + + Cannot save '%1'. + + + + Qt message files for released applications (*.qm) +All files (*) + + + + Release + + + + File created. + + + + Printing... + + + + Context: %1 + + + + finished + + + + unresolved + + + + obsolete + + + + Printing... (page %1) + + + + Printing completed + + + + Printing aborted + + + + Search wrapped. + + + + Cannot find the string '%1'. + + + + Qt phrase books (*.qph) +All files (*) + + + + Create New Phrase Book + + + + A file called '%1' already exists. Please choose another name. + + + + Phrase book created. + + + + %1 phrase(s) loaded. + + + + %1 - %2 + + + + Do you want to save '%1'? + + + + Qt Linguist by Trolltech + + + + No phrase to translate. + + + + No untranslated phrases left. + + + + &File + + + + &Edit + + + + &Translation + + + + V&alidation + + + + &Phrases + + + + &View + + + + &Help + + + + &Open... + + + + Ctrl+O + + + + &Save + + + + Ctrl+S + + + + Save &As... + + + + &Release... + + + + &Print... + + + + Ctrl+P + + + + Re&cently opened files + + + + E&xit + + + + Ctrl+Q + + + + &Undo + + + + Ctrl+Z + + + + &Redo + + + + Ctrl+Y + + + + Cu&t + + + + Ctrl+X + + + + &Copy + + + + Ctrl+C + + + + &Paste + + + + Ctrl+V + + + + Select &All + + + + Ctrl+A + + + + &Find... + + + + Ctrl+F + + + + Find &Next + + + + &Replace... + + + + Ctrl+H + + + + &Prev Unfinished + + + + Ctrl+K + + + + &Next Unfinished + + + + Ctrl+L + + + + P&rev + + + + Ctrl+Shift+K + + + + Ne&xt + + + + Ctrl+Shift+L + + + + Done and &Next + + + + Ctrl+Enter + + + + Ctrl+Return + + + + &Begin from Source + + + + Ctrl+B + + + + &New Phrase Book... + + + + Ctrl+N + + + + &Open Phrase Book... + + + + &Close Phrase Book + + + + &Edit Phrase Book... + + + + &Print Phrase Book... + + + + &Accelerators + + + + &Ending Punctuation + + + + &Phrase Matches + + + + &Revert Sorting + + + + &Display guesses + + + + Vie&ws + + + + &Toolbars + + + + &Manual + + + + &About + + + + About &Qt + + + + &What's This? + + + + Open a Qt translation source file (TS file) for editing. + + + + Save changes made to this Qt translation source file. + + + + Save changes made to this Qt translationsource file into a new file. + + + + Create a Qt message file suitable for released applications from the current message file. + + + + Print a list of all the phrases in the current Qt translation source file. + + + + Close this window and exit. + + + + Undo the last editing operation performed on the translation. + + + + Redo an undone editing operation performed on the translation. + + + + Copy the selected translation text to the clipboard and deletes it. + + + + Copy the selected translation text to the clipboard. + + + + Paste the clipboard text into the translation. + + + + Select the whole translation text. + + + + Search for some text in the translation source file. + + + + Continue the search where it was left. + + + + Search for some text in the translation source file and replace it by another text. + + + + Create a new phrase book. + + + + Open a phrase book to assist translation. + + + + Toggle validity checks of accelerators. + + + + Toggle validity checks of ending punctuation. + + + + Toggle checking that phrase suggestions are used. + + + + Sort the items back in the same order as in the message file. + + + + Set whether or not to display translation guesses. + + + + Display the manual for %1. + + + + Display information about %1. + + + + Display information about the Qt toolkit by Trolltech. + + + + Enter What's This? mode. + + + + Copies the source text into the translation field. + + + + Moves to the next item. + + + + Moves to the previous item. + + + + Moves to the next unfinished item. + + + + Moves to the previous unfinished item. + + + + Marks this item as done and moves to the next unfinished item. + + + + File + + + + Edit + + + + Translation + + + + Validation + + + + Help + + + + Open + + + + Save + + + + Print + + + + Open Phrase Book + + + + Undo + + + + Redo + + + + Cut + + + + Copy + + + + Paste + + + + Find + + + + Replace + + + + Prev + + + + Next + + + + Prev Unfinished + + + + Next Unfinished + + + + Done and Next + + + + Accelerators + + + + Punctuation + + + + Phrases + + + + What's This? + + + + Cannot read from phrase book '%1'. + + + + Close this phrase book. + + + + Allow you to add, modify, or delete phrases of this phrase book. + + + + Print the entries of the phrase book. + + + + Cannot create phrase book '%1'. + + + + Accelerator possibly superfluous in translation. + + + + Accelerator possibly missing in translation. + + + + Translation does not end with the same punctuation as the source text. + + + + A phrase book suggestion for '%1' was ignored. + + + + ... + + + + Version %1 + + + + diff --git a/tools/linguist/linguist/listviews.cpp b/tools/linguist/linguist/listviews.cpp new file mode 100644 index 000000000..843f18db6 --- /dev/null +++ b/tools/linguist/linguist/listviews.cpp @@ -0,0 +1,350 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "listviews.h" + +#include + +static const int Text0MaxLen = 150; +static const int Text1MaxLen = 150; + +/* + LVI implementation +*/ + +static TQString rho( int n ) +{ + TQString s; + s.sprintf( "%.10d", n ); + return s; +} + +int LVI::count = 0; + +LVI::LVI( TQListView * parent, TQString text ) + : TQListViewItem( parent, text ) +{ + setText( 0, rho(count++) ); +} + +LVI::LVI( TQListViewItem * parent, TQString text ) + : TQListViewItem( parent, text ) +{ + setText( 0, rho(count++) ); +} + +/* + This is a cut-down version of TQListViewItem::paintCell() - + it is needed to produce the effect we want on obsolete items + */ +void LVI::drawObsoleteText( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ) +{ + TQListView * lv = listView(); + int marg = lv ? lv->itemMargin() : 1; + int r = marg; + p->fillRect( 0, 0, width, height(), cg.brush( TQColorGroup::Base ) ); + if ( isSelected() && (column==0 || listView()->allColumnsShowFocus()) ) + p->fillRect( r - marg, 0, width - r + marg, height(), + cg.brush( TQColorGroup::Highlight ) ); + + // Do the ellipsis thingy + TQString t = text( column ); + TQString tmp; + int i = 0; + if ( p->fontMetrics().width( t ) > width ) { + tmp = "..."; + while ( p->fontMetrics().width( tmp + t[i] ) < width ) + tmp += t[ i++ ]; + tmp.remove( (uint)0, 3 ); + if ( tmp.isEmpty() ) + tmp = t.left( 1 ); + tmp += "..."; + t = tmp; + } + if ( isSelected() ) + p->setPen( lv->palette().disabled().highlightedText() ); + else + p->setPen( lv->palette().disabled().text() ); + + if ( !t.isEmpty() ) { + p->drawText( r, 0, width-marg-r, height(), + align | AlignVCenter | SingleLine, t ); + } + +} + +int LVI::compare( TQListViewItem *other, int column, bool ascending ) const +{ + TQString thisKey = key( column, ascending ); + TQString otherKey = other->key( column, ascending ); + + if ( thisKey.contains('&') || otherKey.contains('&') ) { + TQString nicerThisKey = thisKey; + TQString nicerOtherKey = otherKey; + + nicerThisKey.replace( "&", "" ); + nicerOtherKey.replace( "&", "" ); + + int delta = nicerThisKey.localeAwareCompare( nicerOtherKey ); + if ( delta != 0 ) + return delta; + } + return thisKey.localeAwareCompare( otherKey ); +} + +static TQString fixEllipsis( const TQString & str, int len ) +{ + TQString shortened = str.simplifyWhiteSpace(); + if ( (int) shortened.length() > len ) { + TQString dots = TrWindow::tr( "..." ); + shortened.truncate( len - dots.length() ); + shortened.append( dots ); + } + return shortened; +} + +/* + MessageLVI implementation +*/ +MessageLVI::MessageLVI( TQListView *parent, + const MetaTranslatorMessage & message, + const TQString& text, const TQString& comment, + ContextLVI * c ) + : LVI( parent ), m( message ), tx( text ), com( comment ), ctxt( c ) +{ + if ( m.translation().isEmpty() ) { + TQString t = ""; + m.setTranslation( t ); + } + setText( 1, fixEllipsis( text, Text0MaxLen ) ); + fini = TRUE; + d = FALSE; + + if( m.type() == MetaTranslatorMessage::Unfinished ) + setFinished( FALSE ); +} + +void MessageLVI::updateTranslationText() +{ + setText( 2, fixEllipsis( m.translation(), Text1MaxLen ) ); +} + +void MessageLVI::paintCell( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ) +{ + if ( column == 0 ) { + int x = (width/2) - TrWindow::pxOn->width()/2; + int y = (height()/2) - TrWindow::pxOn->height()/2; + + int marg = listView() ? listView()->itemMargin() : 1; + int r = marg; + + if ( isSelected() ) + p->fillRect( r - marg, 0, width - r + marg, height(), + cg.brush( TQColorGroup::Highlight ) ); + else + p->fillRect( 0, 0, width, height(), + cg.brush( TQColorGroup::Base ) ); + + if ( m.type() == MetaTranslatorMessage::Unfinished && danger() ) + p->drawPixmap( x, y, *TrWindow::pxDanger ); + else if ( m.type() == MetaTranslatorMessage::Finished ) + p->drawPixmap( x, y, *TrWindow::pxOn ); + else if ( m.type() == MetaTranslatorMessage::Unfinished ) + p->drawPixmap( x, y, *TrWindow::pxOff ); + else if ( m.type() == MetaTranslatorMessage::Obsolete ) + p->drawPixmap( x, y, *TrWindow::pxObsolete ); + } else { + if ( m.type() == MetaTranslatorMessage::Obsolete ) + drawObsoleteText( p, cg, column, width, align ); + else + TQListViewItem::paintCell( p, cg, column, width, align ); + } +} + + +void MessageLVI::setTranslation( const TQString& translation ) +{ + m.setTranslation( translation ); +} + +void MessageLVI::setFinished( bool finished ) +{ + if ( !fini && finished ) { + m.setType( MetaTranslatorMessage::Finished ); + repaint(); + ctxt->decrementUnfinishedCount(); + } else if ( fini && !finished ) { + m.setType( MetaTranslatorMessage::Unfinished ); + repaint(); + ctxt->incrementUnfinishedCount(); + } + fini = finished; +} + +void MessageLVI::setDanger( bool danger ) +{ + if ( !d && danger ) { + ctxt->incrementDangerCount(); + repaint(); + } else if ( d && !danger ) { + ctxt->decrementDangerCount(); + repaint(); + } + d = danger; +} + +TQString MessageLVI::context() const +{ + return TQString( m.context() ); +} + +MetaTranslatorMessage MessageLVI::message() const +{ + return m; +} + +/* + ContextLVI implementation +*/ +ContextLVI::ContextLVI( TQListView *lv, const TQString& context ) + : LVI( lv ), com( "" ) +{ + messageItems.setAutoDelete( TRUE ); + + unfinishedCount = 0; + dangerCount = 0; + obsoleteCount = 0; + itemCount = 0; + setText( 1, context ); +} + +void ContextLVI::instantiateMessageItem( TQListView * lv, MessageLVI * i ) +{ + itemCount++; + appendMessageItem( lv, i ); +} + +void ContextLVI::appendMessageItem( TQListView * lv, MessageLVI * i ) +{ + lv->takeItem( i ); + messageItems.append( i ); +} + +void ContextLVI::updateStatus() +{ + TQString s; + s.sprintf( "%d/%d", itemCount - unfinishedCount - obsoleteCount, + itemCount - obsoleteCount ); + setText( 2, s ); +} + +void ContextLVI::paintCell( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ) +{ + if ( column == 0 ) { + int x = (width/2) - TrWindow::pxOn->width()/2; + int y = (height()/2) - TrWindow::pxOn->height()/2; + + int marg = listView() ? listView()->itemMargin() : 1; + int r = marg; + + if ( isSelected() ) + p->fillRect( r - marg, 0, width - r + marg, height(), + cg.brush( TQColorGroup::Highlight ) ); + else + p->fillRect( 0, 0, width, height(), + cg.brush( TQColorGroup::Base ) ); + + if ( isContextObsolete() ) + p->drawPixmap( x, y, *TrWindow::pxObsolete ); + else if ( unfinishedCount == 0 ) + p->drawPixmap( x, y, *TrWindow::pxOn ); + else + p->drawPixmap( x, y, *TrWindow::pxOff ); + + } else { + if ( isContextObsolete() ) + drawObsoleteText( p, cg, column, width, align ); + else + TQListViewItem::paintCell( p, cg, column, width, align ); + } +} + +void ContextLVI::appendToComment( const TQString& x ) +{ + if ( !com.isEmpty() ) + com += TQString( "\n\n" ); + com += x; +} + +void ContextLVI::incrementUnfinishedCount() +{ + if ( unfinishedCount++ == 0 ) + repaint(); +} + +void ContextLVI::decrementUnfinishedCount() +{ + if ( --unfinishedCount == 0 ) + repaint(); +} + +void ContextLVI::incrementDangerCount() +{ + if ( dangerCount++ == 0 ) + repaint(); +} + +void ContextLVI::decrementDangerCount() +{ + if ( --dangerCount == 0 ) + repaint(); +} + +void ContextLVI::incrementObsoleteCount() +{ + if ( obsoleteCount++ == 0 ) + repaint(); +} + +bool ContextLVI::isContextObsolete() +{ + return (obsoleteCount == itemCount); +} + +TQString ContextLVI::fullContext() const +{ + return comment().stripWhiteSpace(); +} diff --git a/tools/linguist/linguist/listviews.h b/tools/linguist/linguist/listviews.h new file mode 100644 index 000000000..65e0b1f05 --- /dev/null +++ b/tools/linguist/linguist/listviews.h @@ -0,0 +1,135 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef LISTVIEWS_H +#define LISTVIEWS_H + +#include "msgedit.h" + +#include +#include +#include +#include + +class LVI : public TQListViewItem +{ +public: + LVI( TQListView *parent, TQString text = TQString::null ); + LVI( TQListViewItem *parent, TQString text = TQString::null ); + virtual int compare( TQListViewItem *other, int column, + bool ascending ) const; + virtual bool danger() const { return FALSE; } + +protected: + void drawObsoleteText( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ); + +private: + static int count; +}; + +class MessageLVI; +class ContextLVI : public LVI +{ +public: + ContextLVI( TQListView *lv, const TQString& context ); + + virtual bool danger() const { return dangerCount > 0; } + + void appendToComment( const TQString& x ); + void incrementUnfinishedCount(); + void decrementUnfinishedCount(); + void incrementDangerCount(); + void decrementDangerCount(); + void incrementObsoleteCount(); + bool isContextObsolete(); + void updateStatus(); + + TQString context() const { return text( 1 ); } + TQString comment() const { return com; } + TQString fullContext() const; + bool finished() const { return unfinishedCount == 0; } + + MessageLVI * firstMessageItem() { return messageItems.first(); } + MessageLVI * nextMessageItem() { return messageItems.next(); } + MessageLVI * takeMessageItem( int i ) { return messageItems.take( i ); } + void appendMessageItem( TQListView * lv, MessageLVI * i ); + void instantiateMessageItem( TQListView * lv, MessageLVI * i ); + int messageItemsInList() { return messageItems.count(); } + + void paintCell( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ); +private: + TQPtrList messageItems; + TQString com; + int unfinishedCount; + int dangerCount; + int obsoleteCount; + int itemCount; +}; + +class MessageLVI : public LVI +{ +public: + MessageLVI( TQListView *parent, const MetaTranslatorMessage & message, + const TQString& text, const TQString& comment, ContextLVI * c ); + + virtual bool danger() const { return d; } + + void setTranslation( const TQString& translation ); + void setFinished( bool finished ); + void setDanger( bool danger ); + + void setContextLVI( ContextLVI * c ) { ctxt = c; } + ContextLVI * contextLVI() const { return ctxt; } + void updateTranslationText(); + + TQString context() const; + TQString sourceText() const { return tx; } + TQString comment() const { return com; } + TQString translation() const { return m.translation(); } + bool finished() const { return fini; } + MetaTranslatorMessage message() const; + + void paintCell( TQPainter * p, const TQColorGroup & cg, int column, + int width, int align ); +private: + MetaTranslatorMessage m; + TQString tx; + TQString com; + bool fini; + bool d; + ContextLVI * ctxt; +}; + +#endif diff --git a/tools/linguist/linguist/main.cpp b/tools/linguist/linguist/main.cpp new file mode 100644 index 000000000..5e5ef799e --- /dev/null +++ b/tools/linguist/linguist/main.cpp @@ -0,0 +1,89 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "trwindow.h" + +#include +#include +#include +#include +#include +#include +#include +#include + +int main( int argc, char **argv ) +{ + TQApplication app( argc, argv ); + TQApplication::setOverrideCursor( TQt::waitCursor ); + + + TQTranslator translator( 0 ); + translator.load( TQString( "linguist_" ) + TQTextCodec::locale(), "." ); + app.installTranslator( &translator ); + + bool showSplash = TRUE; + + TQString keybase("/TQt Linguist/3.1/"); + TQSettings config; + config.insertSearchPath( TQSettings::Windows, "/Trolltech" ); + + TQRect r( TQApplication::desktop()->screenGeometry() ); + r.setX( config.readNumEntry( keybase + "Geometry/MainwindowX", r.x() ) ); + r.setY( config.readNumEntry( keybase + "Geometry/MainwindowY", r.y() ) ); + r.setWidth( config.readNumEntry( keybase + "Geometry/MainwindowWidth", r.width() ) ); + r.setHeight( config.readNumEntry( keybase + "Geometry/MainwindowHeight", r.height() ) ); + + TQSplashScreen *splash = 0; + if ( showSplash ) { + splash = new TQSplashScreen( TQPixmap::fromMimeSource("splash.png"), + TQt::WDestructiveClose ); + splash->show(); + } + + TrWindow *tw = new TrWindow; + app.setMainWidget( tw ); + + if ( app.argc() > 1 ) + tw->openFile( TQString(app.argv()[app.argc() - 1]) ); + + if ( config.readBoolEntry( keybase + "Geometry/MainwindowMaximized", FALSE ) ) + tw->showMaximized(); + else + tw->show(); + if ( splash ) + splash->finish( tw ); + TQApplication::restoreOverrideCursor(); + + return app.exec(); +} diff --git a/tools/linguist/linguist/msgedit.cpp b/tools/linguist/linguist/msgedit.cpp new file mode 100644 index 000000000..b2ebdef66 --- /dev/null +++ b/tools/linguist/linguist/msgedit.cpp @@ -0,0 +1,834 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +/* TRANSLATOR MsgEdit + + This is the right panel of the main window. +*/ + +#include "msgedit.h" + +#include "trwindow.h" +#include "phraselv.h" +#include "simtexth.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const int MaxCandidates = 5; + +class MED : public TQTextEdit +{ +public: + MED( TQWidget *parent, const char *name = 0 ) + : TQTextEdit( parent, name ) {} + + int cursorX() const { return textCursor()->x(); } + int cursorY() const { return textCursor()->paragraph()->rect().y() + + textCursor()->y(); } +}; + + +TQString richMeta( const TQString& text ) +{ + return TQString( "(" ) + text + + TQString( ")" ); +} + +TQString richText( const TQString& text ) +{ + const char backTab[] = "\a\b\f\n\r\t"; + const char * const friendlyBackTab[] = { + QT_TRANSLATE_NOOP( "MessageEditor", "bell" ), + QT_TRANSLATE_NOOP( "MessageEditor", "backspace" ), + QT_TRANSLATE_NOOP( "MessageEditor", "new page" ), + QT_TRANSLATE_NOOP( "MessageEditor", "new line" ), + QT_TRANSLATE_NOOP( "MessageEditor", "carriage return" ), + QT_TRANSLATE_NOOP( "MessageEditor", "tab" ) + }; + TQString rich; + + for ( int i = 0; i < (int) text.length(); i++ ) { + int ch = text[i].unicode(); + + if ( ch < 0x20 ) { + const char *p = strchr( backTab, ch ); + if ( p == 0 ) + rich += richMeta( TQString::number(ch, 16) ); + else + rich += richMeta( MessageEditor::tr(friendlyBackTab[p - backTab]) ); + } else if ( ch == '<' ) { + rich += TQString( "<" ); + } else if ( ch == '>' ) { + rich += TQString( ">" ); + } else if ( ch == '&' ) { + rich += TQString( "&" ); + } else if ( ch == ' ' ) { + if ( i == 0 || i == (text.length()-1) || text[i - 1] == ' ' || text[i + 1] == ' ' ) { + rich += richMeta( MessageEditor::tr("sp") ); + } else { + rich += ' '; + } + } else { + rich += TQChar( ch ); + } + if ( ch == '\n' ) + rich += TQString( "
" ); + } + return rich; +} + +/* + ShadowWidget class impl. + + Used to create a shadow like effect for a widget +*/ +ShadowWidget::ShadowWidget( TQWidget * parent, const char * name ) + : TQWidget( parent, name ), sWidth( 10 ), wMargin( 3 ), childWgt( 0 ) +{ +} + +ShadowWidget::ShadowWidget( TQWidget * child, TQWidget * parent, + const char * name ) + : TQWidget( parent, name ), sWidth( 10 ), wMargin( 3 ), childWgt( 0 ) +{ + setWidget( child ); +} + +void ShadowWidget::setWidget( TQWidget * child ) +{ + childWgt = child; + if ( childWgt && childWgt->parent() != this ) { + childWgt->reparent( this, TQPoint( 0, 0 ), TRUE ); + } +} + +void ShadowWidget::resizeEvent( TQResizeEvent * ) +{ + if( childWgt ) { + childWgt->move( wMargin, wMargin ); + childWgt->resize( width() - sWidth - wMargin, height() - sWidth - + wMargin ); + } +} + +void ShadowWidget::paintEvent( TQPaintEvent * e ) +{ + TQPainter p; + int w = width() - sWidth; + int h = height() - sWidth; + + + if ( !((w > 0) && (h > 0)) ) + return; + + if ( p.begin( this ) ) { + p.setPen( colorGroup().shadow() ); + + p.drawPoint( w + 5, 6 ); + p.drawLine( w + 3, 6, w + 5, 8 ); + p.drawLine( w + 1, 6, w + 5, 10 ); + int i; + for( i=7; i < h; i += 2 ) + p.drawLine( w, i, w + 5, i + 5 ); + for( i = w - i + h; i > 6; i -= 2 ) + p.drawLine( i, h, i + 5, h + 5 ); + for( ; i > 0 ; i -= 2 ) + p.drawLine( 6, h + 6 - i, i + 5, h + 5 ); + +// p.eraseRect( w, 0, sWidth, 45 ); // Cheap hack for the page curl.. + p.end(); + } + TQWidget::paintEvent( e ); +} + +/* + EditorPage class impl. + + A frame that contains the source text, translated text and any + source code comments and hints. +*/ +EditorPage::EditorPage( TQWidget * parent, const char * name ) + : TQFrame( parent, name ) +{ + setLineWidth( 1 ); + setFrameStyle( TQFrame::Box | TQFrame::Plain ); + + // Use white explicitly as the background color for the editor page. + TQPalette p = palette(); + p.setColor( TQPalette::Active, TQColorGroup::Base, TQColor( white ) ); + p.setColor( TQPalette::Inactive, TQColorGroup::Base, TQColor( white ) ); + p.setColor( TQPalette::Disabled, TQColorGroup::Base, TQColor( white ) ); + p.setColor( TQPalette::Active, TQColorGroup::Background, + p.active().color( TQColorGroup::Base ) ); + p.setColor( TQPalette::Inactive, TQColorGroup::Background, + p.inactive().color( TQColorGroup::Base ) ); + p.setColor( TQPalette::Disabled, TQColorGroup::Background, + p.disabled().color( TQColorGroup::Base ) ); + setPalette( p ); + + srcTextLbl = new TQLabel( tr("Source text"), this, "source text label" ); + transLbl = new TQLabel( tr("Translation"), this, "translation label" ); + + TQFont fnt = font(); + fnt.setBold( TRUE ); + srcTextLbl->setFont( fnt ); + transLbl->setFont( fnt ); + + srcText = new TQTextView( this, "source text view" ); + srcText->setFrameStyle( TQFrame::NoFrame ); + srcText->setSizePolicy( TQSizePolicy( TQSizePolicy::MinimumExpanding, + TQSizePolicy::Minimum ) ); + srcText->setResizePolicy( TQScrollView::AutoOne ); + srcText->setHScrollBarMode( TQScrollView::AlwaysOff ); + srcText->setVScrollBarMode( TQScrollView::AlwaysOff ); + p = srcText->palette(); + p.setColor( TQPalette::Disabled, TQColorGroup::Base, p.active().base() ); + srcText->setPalette( p ); + connect( srcText, SIGNAL(textChanged()), SLOT(handleSourceChanges()) ); + + cmtText = new TQTextView( this, "comment/context view" ); + cmtText->setFrameStyle( TQFrame::NoFrame ); + cmtText->setSizePolicy( TQSizePolicy( TQSizePolicy::MinimumExpanding, + TQSizePolicy::Minimum ) ); + cmtText->setResizePolicy( TQScrollView::AutoOne ); + cmtText->setHScrollBarMode( TQScrollView::AlwaysOff ); + cmtText->setVScrollBarMode( TQScrollView::AlwaysOff ); + p = cmtText->palette(); + p.setColor( TQPalette::Active, TQColorGroup::Base, TQColor( 236,245,255 ) ); + p.setColor( TQPalette::Inactive, TQColorGroup::Base, TQColor( 236,245,255 ) ); + cmtText->setPalette( p ); + connect( cmtText, SIGNAL(textChanged()), SLOT(handleCommentChanges()) ); + + translationMed = new MED( this, "translation editor" ); + translationMed->setFrameStyle( TQFrame::NoFrame ); + translationMed->setSizePolicy( TQSizePolicy( TQSizePolicy::MinimumExpanding, + TQSizePolicy::MinimumExpanding ) ); + translationMed->setHScrollBarMode( TQScrollView::AlwaysOff ); + translationMed->setVScrollBarMode( TQScrollView::AlwaysOff ); + translationMed->setResizePolicy( TQScrollView::AutoOne ); + translationMed->setWrapPolicy( TQTextView::AtWhiteSpace ); + translationMed->setWordWrap( TQTextView::WidgetWidth ); + translationMed->setTextFormat( TQTextView::PlainText ); + p = translationMed->palette(); + p.setColor( TQPalette::Disabled, TQColorGroup::Base, p.active().base() ); + translationMed->setPalette( p ); + connect( translationMed, SIGNAL(textChanged()), + SLOT(handleTranslationChanges()) ); + + pageCurl = new PageCurl( this, "page curl" ); + + // Focus + setFocusPolicy( StrongFocus ); + transLbl->setFocusProxy( translationMed ); + srcTextLbl->setFocusProxy( translationMed ); + cmtText->setFocusProxy( translationMed ); + srcText->setFocusProxy( translationMed ); + setFocusProxy( translationMed ); + + updateCommentField(); +} + +/* + Don't show the comment field if there are no comments. +*/ +void EditorPage::updateCommentField() +{ + if( cmtText->text().isEmpty() ) + cmtText->hide(); + else + cmtText->show(); + + layoutWidgets(); +} + +/* + Handle the widget layout manually +*/ +void EditorPage::layoutWidgets() + { + int margin = 6; + int space = 2; + int w = width(); + + pageCurl->move( width() - pageCurl->width(), 0 ); + + TQFontMetrics fm( srcTextLbl->font() ); + srcTextLbl->move( margin, margin ); + srcTextLbl->resize( fm.width( srcTextLbl->text() ), srcTextLbl->height() ); + + srcText->move( margin, srcTextLbl->y() + srcTextLbl->height() + space ); + srcText->resize( w - margin*2, srcText->height() ); + + cmtText->move( margin, srcText->y() + srcText->height() + space ); + cmtText->resize( w - margin*2, cmtText->height() ); + + if( cmtText->isHidden() ) + transLbl->move( margin, srcText->y() + srcText->height() + space ); + else + transLbl->move( margin, cmtText->y() + cmtText->height() + space ); + transLbl->resize( w - margin*2, transLbl->height() ); + + translationMed->move( margin, transLbl->y() + transLbl->height() + space ); + translationMed->resize( w - margin*2, translationMed->height() ); + + // Calculate the total height for the editor page - emit a signal + // if the actual page size is larger/smaller + int totHeight = margin + srcTextLbl->height() + + srcText->height() + space + + transLbl->height() + space + + translationMed->height() + space + + frameWidth()*lineWidth()*2 + space * 3; + + if( !cmtText->isHidden() ) + totHeight += cmtText->height() + space; + + if( height() != totHeight ) + emit pageHeightUpdated( totHeight ); +} + +void EditorPage::resizeEvent( TQResizeEvent * ) +{ + handleTranslationChanges(); + handleSourceChanges(); + handleCommentChanges(); + layoutWidgets(); +} + +void EditorPage::handleTranslationChanges() +{ + calculateFieldHeight( (TQTextView *) translationMed ); +} + +void EditorPage::handleSourceChanges() +{ + calculateFieldHeight( srcText ); +} + +void EditorPage::handleCommentChanges() +{ + calculateFieldHeight( cmtText ); +} + +/* + Check if the translation text field is big enough to show all text + that has been entered. If it isn't, resize it. +*/ +void EditorPage::calculateFieldHeight( TQTextView * field ) +{ + field->sync(); // make sure the text formatting is done! + int contentsHeight = field->contentsHeight(); + + if( contentsHeight != field->height() ) { + int oldHeight = field->height(); + if( contentsHeight < 30 ) + contentsHeight = 30; + field->resize( field->width(), contentsHeight ); + emit pageHeightUpdated( height() + (field->height() - oldHeight) ); + } +} + +void EditorPage::fontChange( const TQFont & ) +{ + TQFont fnt = font(); + + fnt.setBold( TRUE ); + TQFontMetrics fm( fnt ); + srcTextLbl->setFont( fnt ); + srcTextLbl->resize( fm.width( srcTextLbl->text() ), srcTextLbl->height() ); + transLbl->setFont( fnt ); + transLbl->resize( fm.width( transLbl->text() ), transLbl->height() ); + update(); +} + +/* + MessageEditor class impl. + + Handle layout of dock windows and the editor page. +*/ +MessageEditor::MessageEditor( MetaTranslator * t, TQWidget * parent, + const char * name ) + : TQWidget( parent, name ), + tor( t ) +{ + doGuesses = TRUE; + v = new TQVBoxLayout( this ); + topDock = new TQDockArea( TQt::Horizontal, TQDockArea::Normal, this, + "top dock area" ); + topDock->setMinimumHeight( 10 ); + topDock->setSizePolicy( TQSizePolicy( TQSizePolicy::Minimum, + TQSizePolicy::Minimum) ); + + topDockWnd = new TQDockWindow( TQDockWindow::InDock, topDock, + "top dock window" ); + TQMainWindow *mw = (TQMainWindow*)topLevelWidget(); + if ( mw ) { + mw->setDockEnabled( topDockWnd, TQt::DockTop, TRUE ); + mw->setDockEnabled( topDockWnd, TQt::DockLeft, TRUE ); + mw->setDockEnabled( topDockWnd, TQt::DockRight, TRUE ); + mw->setDockEnabled( topDockWnd, TQt::DockBottom, TRUE ); + } + + topDockWnd->setCaption( tr("Source text") ); + topDockWnd->setCloseMode( TQDockWindow::Always ); + topDockWnd->setResizeEnabled( TRUE ); + topDockWnd->setFixedExtentHeight( 110 ); + + srcTextList = new TQListView( topDockWnd, "source text list view" ); + srcTextList->setShowSortIndicator( TRUE ); + srcTextList->setAllColumnsShowFocus( TRUE ); + srcTextList->setSorting( 0 ); + TQFontMetrics fm( font() ); + srcTextList->addColumn( tr("Done"), fm.width( tr("Done") ) + 10 ); + srcTextList->addColumn( tr("Source text") ); + srcTextList->addColumn( tr("Translation"), 300 ); + srcTextList->setColumnAlignment( 0, TQt::AlignCenter ); + srcTextList->setColumnWidthMode( 1, TQListView::Manual ); + srcTextList->header()->setStretchEnabled( TRUE, 1 ); + srcTextList->setMinimumSize( TQSize( 50, 50 ) ); + srcTextList->setHScrollBarMode( TQScrollView::AlwaysOff ); + srcTextList->installEventFilter( this ); + topDockWnd->setWidget( srcTextList ); + + sv = new TQScrollView( this, "scroll view" ); + sv->setHScrollBarMode( TQScrollView::AlwaysOff ); + sv->viewport()->setBackgroundMode( PaletteBackground ); + + editorPage = new EditorPage( sv, "editor page" ); + connect( editorPage, SIGNAL(pageHeightUpdated(int)), + SLOT(updatePageHeight(int)) ); + + editorPage->translationMed->installEventFilter( this ); + + sw = new ShadowWidget( editorPage, sv, "editor page shadow" ); + sw->setSizePolicy( TQSizePolicy( TQSizePolicy::Expanding, + TQSizePolicy::Expanding) ); + sw->setMinimumSize( TQSize( 100, 150 ) ); + sv->addChild( sw ); + + bottomDock = new TQDockArea( TQt::Horizontal, TQDockArea::Reverse, + this, "bottom dock area" ); + bottomDock->setMinimumHeight( 10 ); + bottomDock->setSizePolicy( TQSizePolicy( TQSizePolicy::Minimum, + TQSizePolicy::Minimum) ); + bottomDockWnd = new TQDockWindow( TQDockWindow::InDock, bottomDock, + "bottom dock window" ); + if ( mw ) { + mw->setDockEnabled( bottomDockWnd, TQt::DockTop, TRUE ); + mw->setDockEnabled( bottomDockWnd, TQt::DockLeft, TRUE ); + mw->setDockEnabled( bottomDockWnd, TQt::DockRight, TRUE ); + mw->setDockEnabled( bottomDockWnd, TQt::DockBottom, TRUE ); + } + bottomDockWnd->setCaption( tr("Phrases") ); + bottomDockWnd->setCloseMode( TQDockWindow::Always ); + bottomDockWnd->setResizeEnabled( TRUE ); + + TQWidget * w = new TQWidget( bottomDockWnd ); + w->setSizePolicy( TQSizePolicy( TQSizePolicy::Minimum, + TQSizePolicy::Minimum ) ); + TQHBoxLayout *hl = new TQHBoxLayout( w, 6 ); + TQVBoxLayout *vl = new TQVBoxLayout( 6 ); + + phraseLbl = new TQLabel( tr("Phrases and guesses:"), w ); + phraseLv = new PhraseLV( w, "phrase list view" ); + phraseLv->setSorting( PhraseLVI::DefinitionText ); + phraseLv->installEventFilter( this ); + hl->addLayout( vl ); + vl->addWidget( phraseLbl ); + vl->addWidget( phraseLv ); + + accel = new TQAccel( this, "accel" ); + connect( accel, SIGNAL(activated(int)), this, SLOT(guessActivated(int)) ); + for ( int i = 0; i < 9; i++ ) + accel->insertItem( CTRL + (Key_1 + i), i + 1 ); + + bottomDockWnd->setWidget( w ); + + v->addWidget( topDock ); + v->addWidget( sv ); + v->addWidget( bottomDock ); + + // Signals + connect( editorPage->pageCurl, SIGNAL(nextPage()), + SIGNAL(nextUnfinished()) ); + connect( editorPage->pageCurl, SIGNAL(prevPage()), + SIGNAL(prevUnfinished()) ); + + connect( editorPage->translationMed, SIGNAL(textChanged()), + this, SLOT(emitTranslationChanged()) ); + connect( editorPage->translationMed, SIGNAL(textChanged()), + this, SLOT(updateButtons()) ); + connect( editorPage->translationMed, SIGNAL(undoAvailable(bool)), + this, SIGNAL(undoAvailable(bool)) ); + connect( editorPage->translationMed, SIGNAL(redoAvailable(bool)), + this, SIGNAL(redoAvailable(bool)) ); + connect( editorPage->translationMed, SIGNAL(copyAvailable(bool)), + this, SIGNAL(cutAvailable(bool)) ); + connect( editorPage->translationMed, SIGNAL(copyAvailable(bool)), + this, SIGNAL(copyAvailable(bool)) ); + connect( qApp->clipboard(), SIGNAL(dataChanged()), + this, SLOT(updateCanPaste()) ); + connect( phraseLv, SIGNAL(doubleClicked(TQListViewItem *)), + this, SLOT(insertPhraseInTranslation(TQListViewItem *)) ); + connect( phraseLv, SIGNAL(returnPressed(TQListViewItem *)), + this, SLOT(insertPhraseInTranslationAndLeave(TQListViewItem *)) ); + + // What's this + TQWhatsThis::add( this, tr("This whole panel allows you to view and edit " + "the translation of some source text.") ); + TQWhatsThis::add( editorPage->srcText, + tr("This area shows the source text.") ); + TQWhatsThis::add( editorPage->cmtText, tr("This area shows a comment that" + " may guide you, and the context in which the text" + " occurs.") ); + TQWhatsThis::add( editorPage->translationMed, + tr("This is where you can enter or modify" + " the translation of some source text.") ); +} + +void MessageEditor::toggleFinished() +{ + if ( itemFinished ) + itemFinished = FALSE; + else + itemFinished = TRUE; + emit finished( itemFinished ); +} + +bool MessageEditor::eventFilter( TQObject *o, TQEvent *e ) +{ + // Handle keypresses in the message editor - scroll the view if the current + // line is hidden. + if ( e->type() == TQEvent::KeyPress || e->type() == TQEvent::KeyRelease ) { + TQKeyEvent * ke = (TQKeyEvent*)e; + const int k = ke->key(); + + if ( ::qt_cast(o) ) { + if ( e->type() == TQEvent::KeyPress ) { + // Hardcode the Tab key to do focus changes when pressed + // inside the editor + if ( k == Key_BackTab ) { + emit focusSourceList(); + return TRUE; + } + } else if ( e->type() == TQEvent::KeyRelease ) { + MED * ed = (MED *) o; + switch( k ) { + case Key_Up: + if (ed->cursorY() < 10) + sv->verticalScrollBar()->subtractLine(); + break; + + case Key_Down: + if (ed->cursorY() >= ed->height() - 20) + sv->verticalScrollBar()->addLine(); + break; + + case Key_PageUp: + if (ed->cursorY() < 10) + sv->verticalScrollBar()->subtractPage(); + break; + + case Key_PageDown: + if (ed->cursorY() >= ed->height() - 50) + sv->verticalScrollBar()->addPage(); + break; + default: + sv->ensureVisible( sw->margin() + ed->x() + ed->cursorX(), + sw->margin() + ed->y() + ed->cursorY() ); + break; + } + } + } else if ( ::qt_cast(o) ) { + // handle the ESC key in the list views + if ( e->type() == TQEvent::KeyRelease && k == Key_Escape ) + editorPage->translationMed->setFocus(); + } + } + return TQWidget::eventFilter( o, e ); +} + +void MessageEditor::updatePageHeight( int height ) +{ + sw->resize( sw->width(), height + sw->margin() + sw->shadowWidth() ); +} + +void MessageEditor::resizeEvent( TQResizeEvent * ) +{ + sw->resize( sv->viewport()->width(), sw->height() ); +} + +TQListView * MessageEditor::sourceTextList() const +{ + return srcTextList; +} + +TQListView * MessageEditor::phraseList() const +{ + return phraseLv; +} + +void MessageEditor::showNothing() +{ + editorPage->srcText->setText( "" ); + showContext( TQString(""), FALSE ); +} + +void MessageEditor::showContext( const TQString& context, bool finished ) +{ + setEditionEnabled( FALSE ); + sourceText = TQString::null; + guesses.clear(); + + if( context.isEmpty() ) + editorPage->cmtText->setText(""); + else + editorPage->cmtText->setText( richText(context.simplifyWhiteSpace()) ); + setTranslation( TQString(""), FALSE ); + setFinished( finished ); + phraseLv->clear(); + editorPage->handleSourceChanges(); + editorPage->handleCommentChanges(); + editorPage->handleTranslationChanges(); + editorPage->updateCommentField(); +} + +void MessageEditor::showMessage( const TQString& text, + const TQString& comment, + const TQString& fullContext, + const TQString& translation, + MetaTranslatorMessage::Type type, + const TQValueList& phrases ) +{ + bool obsolete = ( type == MetaTranslatorMessage::Obsolete ); + setEditionEnabled( !obsolete ); + sourceText = text; + guesses.clear(); + + editorPage->srcText->setText( TQString("

") + richText( text ) + + TQString("

") ); + + if ( !fullContext.isEmpty() && !comment.isEmpty() ) + editorPage->cmtText->setText( richText(fullContext.simplifyWhiteSpace()) + + "\n" + richText(comment.simplifyWhiteSpace()) ); + else if ( !fullContext.isEmpty() && comment.isEmpty() ) + editorPage->cmtText->setText(richText(fullContext.simplifyWhiteSpace() ) ); + else if ( fullContext.isEmpty() && !comment.isEmpty() ) + editorPage->cmtText->setText( richText(comment.simplifyWhiteSpace() ) ); + else + editorPage->cmtText->setText( "" ); + + setTranslation( translation, FALSE ); + setFinished( type != MetaTranslatorMessage::Unfinished ); + TQValueList::ConstIterator p; + phraseLv->clear(); + for ( p = phrases.begin(); p != phrases.end(); ++p ) + (void) new PhraseLVI( phraseLv, *p ); + + if ( doGuesses && !sourceText.isEmpty() ) { + CandidateList cl = similarTextHeuristicCandidates( tor, + sourceText.latin1(), + MaxCandidates ); + int n = 0; + TQValueList::Iterator it = cl.begin(); + while ( it != cl.end() ) { + TQString def; + if ( n < 9 ) + def = tr( "Guess (%1)" ).arg( TQString(TQKeySequence(CTRL | (Key_0 + (n + 1)))) ); + else + def = tr( "Guess" ); + (void) new PhraseLVI( phraseLv, + Phrase((*it).source, (*it).target, def), + n + 1 ); + n++; + ++it; + } + } + editorPage->handleSourceChanges(); + editorPage->handleCommentChanges(); + editorPage->handleTranslationChanges(); + editorPage->updateCommentField(); +} + +void MessageEditor::setTranslation( const TQString& translation, bool emitt ) +{ + // Block signals so that 'textChanged()' is not emitted when + // for example a new source text item is selected and *not* + // the actual translation. + editorPage->translationMed->blockSignals( !emitt ); + editorPage->translationMed->setText( translation ); + editorPage->translationMed->blockSignals( FALSE ); + if ( !emitt ) + updateButtons(); + emit cutAvailable( FALSE ); + emit copyAvailable( FALSE ); +} + +void MessageEditor::setEditionEnabled( bool enabled ) +{ + editorPage->transLbl->setEnabled( enabled ); + editorPage->translationMed->setReadOnly( !enabled ); + + phraseLbl->setEnabled( enabled ); + phraseLv->setEnabled( enabled ); + updateCanPaste(); +} + +void MessageEditor::undo() +{ + editorPage->translationMed->undo(); +} + +void MessageEditor::redo() +{ + editorPage->translationMed->redo(); +} + +void MessageEditor::cut() +{ + editorPage->translationMed->cut(); +} + +void MessageEditor::copy() +{ + editorPage->translationMed->copy(); +} + +void MessageEditor::paste() +{ + editorPage->translationMed->paste(); +} + +void MessageEditor::del() +{ + editorPage->translationMed->del(); +} + +void MessageEditor::selectAll() +{ + editorPage->translationMed->selectAll(); +} + +void MessageEditor::emitTranslationChanged() +{ + emit translationChanged( editorPage->translationMed->text() ); +} + +void MessageEditor::guessActivated( int accelKey ) +{ + TQListViewItem *item = phraseLv->firstChild(); + while ( item != 0 && ((PhraseLVI *) item)->accelKey() != accelKey ) + item = item->nextSibling(); + if ( item != 0 ) + insertPhraseInTranslation( item ); +} + +void MessageEditor::insertPhraseInTranslation( TQListViewItem *item ) +{ + editorPage->translationMed->insert(((PhraseLVI *) item)->phrase().target()); + emit translationChanged( editorPage->translationMed->text() ); +} + +void MessageEditor::insertPhraseInTranslationAndLeave( TQListViewItem *item ) +{ + editorPage->translationMed->insert(((PhraseLVI *) item)->phrase().target()); + emit translationChanged( editorPage->translationMed->text() ); + editorPage->translationMed->setFocus(); +} + +void MessageEditor::updateButtons() +{ + bool overwrite = ( !editorPage->translationMed->isReadOnly() && + (editorPage->translationMed->text().stripWhiteSpace().isEmpty() || + mayOverwriteTranslation) ); + mayOverwriteTranslation = FALSE; + emit updateActions( overwrite ); +} + +void MessageEditor::beginFromSource() +{ + mayOverwriteTranslation = TRUE; + setTranslation( sourceText, TRUE ); + if ( !editorPage->hasFocus() ) + editorPage->setFocus(); +} + +void MessageEditor::finishAndNext() +{ + setFinished( TRUE ); + emit nextUnfinished(); + if ( !editorPage->hasFocus() ) + editorPage->setFocus(); +} + +void MessageEditor::updateCanPaste() +{ + bool oldCanPaste = canPaste; + canPaste = ( !editorPage->translationMed->isReadOnly() && + !qApp->clipboard()->text().isNull() ); + if ( canPaste != oldCanPaste ) + emit pasteAvailable( canPaste ); +} + +void MessageEditor::setFinished( bool finished ) +{ + if ( !finished != !itemFinished ) + toggleFinished(); +} + +void MessageEditor::toggleGuessing() +{ + doGuesses = !doGuesses; + if ( !doGuesses ) { + phraseLv->clear(); + } +} diff --git a/tools/linguist/linguist/msgedit.h b/tools/linguist/linguist/msgedit.h new file mode 100644 index 000000000..c051e6825 --- /dev/null +++ b/tools/linguist/linguist/msgedit.h @@ -0,0 +1,244 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef MSGEDIT_H +#define MSGEDIT_H + +#include "trwindow.h" +#include "phrase.h" + +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +class TQAccel; +class TQDockArea; +class TQDockWindow; +class TQLabel; +class TQListView; +class TQListViewItem; +class TQTextView; +class TQVBoxLayout; + +class EditorPage; +class MED; +class PhraseLV; + +class PageCurl : public TQWidget +{ + Q_OBJECT +public: + PageCurl( TQWidget * parent = 0, const char * name = 0, + WFlags f = 0 ) + : TQWidget( parent, name, f ) + { + TQPixmap px = TrWindow::pageCurl(); + if ( px.mask() ) { + setMask( *px.mask() ); + } + setBackgroundPixmap( px ); + setFixedSize( px.size() ); + + TQRect r( 34, 0, width()-34, 19 ); + TQToolTip::add( this, r, tr("Next unfinished phrase") ); + r.setSize( TQSize(width()-34, height()-20) ); + r.setX( 0 ); + r.setY( 20 ); + TQToolTip::add( this, r, tr("Previous unfinished phrase") ); + } + +protected: + void mouseReleaseEvent( TQMouseEvent * e ) + { + int x = e->pos().x() - 14; + int y = e->pos().y() - 8; + + if ( y <= x ) + emit nextPage(); + else + emit prevPage(); + } + +signals: + void prevPage(); + void nextPage(); +}; + +class ShadowWidget : public TQWidget +{ +public: + ShadowWidget( TQWidget * parent = 0, const char * name = 0 ); + ShadowWidget( TQWidget * child, TQWidget * parent = 0, const char * name = 0 ); + + void setShadowWidth( int width ) { sWidth = width; } + int shadowWidth() const { return sWidth; } + void setMargin( int margin ){ wMargin = margin; } + int margin() const { return wMargin; } + void setWidget( TQWidget * child); + +protected: + void resizeEvent( TQResizeEvent * e ); + void paintEvent( TQPaintEvent * e ); + +private: + int sWidth; + int wMargin; + TQWidget * childWgt; +}; + +class EditorPage : public TQFrame +{ + Q_OBJECT +public: + EditorPage( TQWidget * parent = 0, const char * name = 0 ); + +protected: + void resizeEvent( TQResizeEvent * ); + void layoutWidgets(); + void updateCommentField(); + void calculateFieldHeight( TQTextView * field ); + void fontChange( const TQFont & ); + +private: + PageCurl * pageCurl; + TQLabel * srcTextLbl; + TQLabel * transLbl; + TQTextView * srcText; + TQTextView * cmtText; + MED * translationMed; + + friend class MessageEditor; + +private slots: + void handleTranslationChanges(); + void handleSourceChanges(); + void handleCommentChanges(); + +signals: + void pageHeightUpdated( int height ); +}; + +class MessageEditor : public TQWidget +{ + Q_OBJECT +public: + MessageEditor( MetaTranslator * t, TQWidget * parent = 0, + const char * name = 0 ); + TQListView * sourceTextList() const; + TQListView * phraseList() const; + + void showNothing(); + void showContext( const TQString& context, bool finished ); + void showMessage( const TQString& text, const TQString& comment, + const TQString& fullContext, const TQString& translation, + MetaTranslatorMessage::Type type, + const TQValueList& phrases ); + void setFinished( bool finished ); + bool eventFilter( TQObject *, TQEvent * ); + +signals: + void translationChanged( const TQString& translation ); + void finished( bool finished ); + void prevUnfinished(); + void nextUnfinished(); + void updateActions( bool enable ); + + void undoAvailable( bool avail ); + void redoAvailable( bool avail ); + void cutAvailable( bool avail ); + void copyAvailable( bool avail ); + void pasteAvailable( bool avail ); + + void focusSourceList(); + void focusPhraseList(); + +public slots: + void undo(); + void redo(); + void cut(); + void copy(); + void paste(); + void del(); + void selectAll(); + void beginFromSource(); + void toggleGuessing(); + void finishAndNext(); + +private slots: + void emitTranslationChanged(); + void guessActivated( int accelKey ); + void insertPhraseInTranslation( TQListViewItem *item ); + void insertPhraseInTranslationAndLeave( TQListViewItem *item ); + void updateButtons(); + void updateCanPaste(); + void toggleFinished(); + + void updatePageHeight( int height ); + +protected: + void resizeEvent( TQResizeEvent * ); + +private: + void setTranslation( const TQString& translation, bool emitt ); + void setEditionEnabled( bool enabled ); + + TQListView * srcTextList; + TQDockArea * topDock, * bottomDock; + TQDockWindow * topDockWnd, *bottomDockWnd; + EditorPage * editorPage; + TQVBoxLayout * v; + + TQLabel * phraseLbl; + PhraseLV * phraseLv; + TQAccel * accel; + bool itemFinished; + + ShadowWidget * sw; + TQScrollView * sv; + + MetaTranslator *tor; + TQString sourceText; + TQStringList guesses; + bool mayOverwriteTranslation; + bool canPaste; + bool doGuesses; +}; + +#endif diff --git a/tools/linguist/linguist/phrase.cpp b/tools/linguist/linguist/phrase.cpp new file mode 100644 index 000000000..8e2dfb8ba --- /dev/null +++ b/tools/linguist/linguist/phrase.cpp @@ -0,0 +1,189 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "phrase.h" + +#include +#include +#include +#include +#include +#include +#include + +static TQString protect( const TQString& str ) +{ + TQString p = str; + p.replace( "&", "&" ); + p.replace( "\"", """ ); + p.replace( ">", ">" ); + p.replace( "<", "<" ); + p.replace( "'", "'" ); + return p; +} + +Phrase::Phrase( const TQString& source, const TQString& target, + const TQString& definition ) + : s( source ), t( target ), d( definition ) +{ +} + +bool operator==( const Phrase& p, const Phrase& q ) +{ + return p.source() == q.source() && p.target() == q.target() && + p.definition() == q.definition(); +} + +class QphHandler : public TQXmlDefaultHandler +{ +public: + QphHandler( PhraseBook *phraseBook ) + : pb( phraseBook ), ferrorCount( 0 ) { } + + virtual bool startElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName, + const TQXmlAttributes& atts ); + virtual bool endElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName ); + virtual bool characters( const TQString& ch ); + virtual bool fatalError( const TQXmlParseException& exception ); + +private: + PhraseBook *pb; + TQString source; + TQString target; + TQString definition; + + TQString accum; + int ferrorCount; +}; + +bool QphHandler::startElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName, + const TQXmlAttributes& /* atts */ ) +{ + if ( qName == TQString("phrase") ) { + source.truncate( 0 ); + target.truncate( 0 ); + definition.truncate( 0 ); + } + accum.truncate( 0 ); + return TRUE; +} + +bool QphHandler::endElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName ) +{ + if ( qName == TQString("source") ) + source = accum; + else if ( qName == TQString("target") ) + target = accum; + else if ( qName == TQString("definition") ) + definition = accum; + else if ( qName == TQString("phrase") ) + pb->append( Phrase(source, target, definition) ); + return TRUE; +} + +bool QphHandler::characters( const TQString& ch ) +{ + accum += ch; + return TRUE; +} + +bool QphHandler::fatalError( const TQXmlParseException& exception ) +{ + if ( ferrorCount++ == 0 ) { + TQString msg; + msg.sprintf( "Parse error at line %d, column %d (%s).", + exception.lineNumber(), exception.columnNumber(), + exception.message().latin1() ); + TQMessageBox::information( qApp->mainWidget(), + TQObject::tr("TQt Linguist"), msg ); + } + return FALSE; +} + +bool PhraseBook::load( const TQString& filename ) +{ + TQFile f( filename ); + if ( !f.open(IO_ReadOnly) ) + return FALSE; + + TQTextStream t( &f ); + TQXmlInputSource in( t ); + TQXmlSimpleReader reader; + // don't click on these! + reader.setFeature( "http://xml.org/sax/features/namespaces", FALSE ); + reader.setFeature( "http://xml.org/sax/features/namespace-prefixes", TRUE ); + reader.setFeature( "http://trolltech.com/xml/features/report-whitespace" + "-only-CharData", FALSE ); + TQXmlDefaultHandler *hand = new QphHandler( this ); + reader.setContentHandler( hand ); + reader.setErrorHandler( hand ); + + bool ok = reader.parse( in ); + reader.setContentHandler( 0 ); + reader.setErrorHandler( 0 ); + delete hand; + f.close(); + if ( !ok ) + clear(); + return ok; +} + +bool PhraseBook::save( const TQString& filename ) const +{ + TQFile f( filename ); + if ( !f.open(IO_WriteOnly) ) + return FALSE; + + TQTextStream t( &f ); + t.setEncoding(TQTextStream::UnicodeUTF8); + t << "\n"; + ConstIterator p; + for ( p = begin(); p != end(); ++p ) { + t << "\n"; + t << " " << protect( (*p).source() ) << "\n"; + t << " " << protect( (*p).target() ) << "\n"; + if ( !(*p).definition().isEmpty() ) + t << " " << protect( (*p).definition() ) + << "\n"; + t << "\n"; + } + t << "\n"; + f.close(); + return TRUE; +} diff --git a/tools/linguist/linguist/phrase.h b/tools/linguist/linguist/phrase.h new file mode 100644 index 000000000..07e5ef385 --- /dev/null +++ b/tools/linguist/linguist/phrase.h @@ -0,0 +1,74 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef PHRASE_H +#define PHRASE_H + +#include +#include + +class Phrase +{ +public: + Phrase() { } + Phrase( const TQString& source, const TQString& target, + const TQString& definition ); + + TQString source() const { return s; } + void setSource( const TQString& ns ) { s = ns; } + TQString target() const { return t; } + void setTarget( const TQString& nt ) { t = nt; } + TQString definition() const { return d; } + void setDefinition ( const TQString& nd ) { d = nd; } + +private: + TQString s; + TQString t; + TQString d; +}; + +bool operator==( const Phrase& p, const Phrase& q ); +inline bool operator!=( const Phrase& p, const Phrase& q ) { + return !( p == q ); +} + +class PhraseBook : public TQValueList +{ +public: + PhraseBook() { } + + bool load( const TQString& filename ); + bool save( const TQString& filename ) const; +}; + +#endif diff --git a/tools/linguist/linguist/phrasebookbox.cpp b/tools/linguist/linguist/phrasebookbox.cpp new file mode 100644 index 000000000..72d4fa550 --- /dev/null +++ b/tools/linguist/linguist/phrasebookbox.cpp @@ -0,0 +1,244 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +/* TRANSLATOR PhraseBookBox + + Go to Phrase > Edit Phrase Book... The dialog that pops up is a + PhraseBookBox. +*/ + +#include "phrasebookbox.h" +#include "phraselv.h" + +#include +#include +#include +#include +#include +#include +#include + +PhraseBookBox::PhraseBookBox( const TQString& filename, + const PhraseBook& phraseBook, TQWidget *parent, + const char *name, bool modal ) + : TQDialog( parent, name, modal ), fn( filename ), pb( phraseBook ) +{ + TQGridLayout *gl = new TQGridLayout( this, 4, 3, 11, 11, + "phrase book outer layout" ); + TQVBoxLayout *bl = new TQVBoxLayout( 6, "phrase book button layout" ); + + sourceLed = new TQLineEdit( this, "source line edit" ); + TQLabel *source = new TQLabel( sourceLed, tr("S&ource phrase:"), this, + "source label" ); + targetLed = new TQLineEdit( this, "target line edit" ); + TQLabel *target = new TQLabel( targetLed, tr("&Translation:"), this, + "target label" ); + definitionLed = new TQLineEdit( this, "definition line edit" ); + TQLabel *definition = new TQLabel( definitionLed, tr("&Definition:"), this, + "target label" ); + lv = new PhraseLV( this, "phrase book list view" ); + + newBut = new TQPushButton( tr("&New Phrase"), this ); + newBut->setDefault( TRUE ); + + removeBut = new TQPushButton( tr("&Remove Phrase"), this ); + removeBut->setEnabled( FALSE ); + TQPushButton *saveBut = new TQPushButton( tr("&Save"), this ); + TQPushButton *closeBut = new TQPushButton( tr("Close"), this ); + + gl->addWidget( source, 0, 0 ); + gl->addWidget( sourceLed, 0, 1 ); + gl->addWidget( target, 1, 0 ); + gl->addWidget( targetLed, 1, 1 ); + gl->addWidget( definition, 2, 0 ); + gl->addWidget( definitionLed, 2, 1 ); + gl->addMultiCellWidget( lv, 3, 3, 0, 1 ); + gl->addMultiCell( bl, 0, 3, 2, 2 ); + + bl->addWidget( newBut ); + bl->addWidget( removeBut ); + bl->addWidget( saveBut ); + bl->addWidget( closeBut ); + bl->addStretch( 1 ); + + connect( sourceLed, SIGNAL(textChanged(const TQString&)), + this, SLOT(sourceChanged(const TQString&)) ); + connect( targetLed, SIGNAL(textChanged(const TQString&)), + this, SLOT(targetChanged(const TQString&)) ); + connect( definitionLed, SIGNAL(textChanged(const TQString&)), + this, SLOT(definitionChanged(const TQString&)) ); + connect( lv, SIGNAL(selectionChanged(TQListViewItem *)), + this, SLOT(selectionChanged(TQListViewItem *)) ); + connect( newBut, SIGNAL(clicked()), this, SLOT(newPhrase()) ); + connect( removeBut, SIGNAL(clicked()), this, SLOT(removePhrase()) ); + connect( saveBut, SIGNAL(clicked()), this, SLOT(save()) ); + connect( closeBut, SIGNAL(clicked()), this, SLOT(accept()) ); + + PhraseBook::ConstIterator it; + for ( it = phraseBook.begin(); it != phraseBook.end(); ++it ) + (void) new PhraseLVI( lv, (*it) ); + enableDisable(); + + TQWhatsThis::add( this, tr("This window allows you to add, modify, or delete" + " phrases in a phrase book.") ); + TQWhatsThis::add( sourceLed, tr("This is the phrase in the source" + " language.") ); + TQWhatsThis::add( targetLed, tr("This is the phrase in the target language" + " corresponding to the source phrase.") ); + TQWhatsThis::add( definitionLed, tr("This is a definition for the source" + " phrase.") ); + TQWhatsThis::add( newBut, tr("Click here to add the phrase to the phrase" + " book.") ); + TQWhatsThis::add( removeBut, tr("Click here to remove the phrase from the" + " phrase book.") ); + TQWhatsThis::add( saveBut, tr("Click here to save the changes made.") ); + TQWhatsThis::add( closeBut, tr("Click here to close this window.") ); +} + +void PhraseBookBox::keyPressEvent( TQKeyEvent *ev ) +{ + if ( ev->key() == Key_Down || ev->key() == Key_Up || + ev->key() == Key_Next || ev->key() == Key_Prior ) + TQApplication::sendEvent( lv, + new TQKeyEvent(ev->type(), ev->key(), ev->ascii(), ev->state(), + ev->text(), ev->isAutoRepeat(), ev->count()) ); + else + TQDialog::keyPressEvent( ev ); +} + +void PhraseBookBox::newPhrase() +{ + Phrase ph; + ph.setSource( NewPhrase ); + TQListViewItem *item = new PhraseLVI( lv, ph ); + selectItem( item ); +} + +void PhraseBookBox::removePhrase() +{ + TQListViewItem *item = lv->currentItem(); + TQListViewItem *next = item->itemBelow() != 0 ? item->itemBelow() + : item->itemAbove(); + delete item; + if ( next != 0 ) + selectItem( next ); + enableDisable(); +} + +void PhraseBookBox::save() +{ + pb.clear(); + TQListViewItem *item = lv->firstChild(); + while ( item != 0 ) { + if ( !item->text(PhraseLVI::SourceTextShown).isEmpty() && + item->text(PhraseLVI::SourceTextShown) != NewPhrase ) + pb.append( Phrase(((PhraseLVI *) item)->phrase()) ); + item = item->nextSibling(); + } + if ( !pb.save( fn ) ) + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("Cannot save phrase book '%1'.").arg(fn) ); +} + +void PhraseBookBox::sourceChanged( const TQString& source ) +{ + if ( lv->currentItem() != 0 ) { + lv->currentItem()->setText( PhraseLVI::SourceTextShown, + source.stripWhiteSpace() ); + lv->currentItem()->setText( PhraseLVI::SourceTextOriginal, source ); + lv->sort(); + lv->ensureItemVisible( lv->currentItem() ); + } +} + +void PhraseBookBox::targetChanged( const TQString& target ) +{ + if ( lv->currentItem() != 0 ) { + lv->currentItem()->setText( PhraseLVI::TargetTextShown, + target.stripWhiteSpace() ); + lv->currentItem()->setText( PhraseLVI::TargetTextOriginal, target ); + lv->sort(); + lv->ensureItemVisible( lv->currentItem() ); + } +} + +void PhraseBookBox::definitionChanged( const TQString& definition ) +{ + if ( lv->currentItem() != 0 ) { + lv->currentItem()->setText( PhraseLVI::DefinitionText, definition ); + lv->sort(); + lv->ensureItemVisible( lv->currentItem() ); + } +} + +void PhraseBookBox::selectionChanged( TQListViewItem * /* item */ ) +{ + enableDisable(); +} + +void PhraseBookBox::selectItem( TQListViewItem *item ) +{ + lv->setSelected( item, TRUE ); + lv->ensureItemVisible( item ); +} + +void PhraseBookBox::enableDisable() +{ + TQListViewItem *item = lv->currentItem(); + + sourceLed->blockSignals( TRUE ); + targetLed->blockSignals( TRUE ); + definitionLed->blockSignals( TRUE ); + + if ( item == 0 ) { + sourceLed->setText( TQString::null ); + targetLed->setText( TQString::null ); + definitionLed->setText( TQString::null ); + } else { + sourceLed->setText( item->text(0) ); + targetLed->setText( item->text(1) ); + definitionLed->setText( item->text(2) ); + } + sourceLed->setEnabled( item != 0 ); + targetLed->setEnabled( item != 0 ); + definitionLed->setEnabled( item != 0 ); + removeBut->setEnabled( item != 0 ); + + sourceLed->blockSignals( FALSE ); + targetLed->blockSignals( FALSE ); + definitionLed->blockSignals( FALSE ); + + TQLineEdit *led = ( sourceLed->text() == NewPhrase ? sourceLed : targetLed ); + led->setFocus(); + led->selectAll(); +} diff --git a/tools/linguist/linguist/phrasebookbox.h b/tools/linguist/linguist/phrasebookbox.h new file mode 100644 index 000000000..ce3b81110 --- /dev/null +++ b/tools/linguist/linguist/phrasebookbox.h @@ -0,0 +1,84 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef PHRASEBOOKBOX_H +#define PHRASEBOOKBOX_H + +#include "phrase.h" + +#include +#include + +class TQLineEdit; +class TQPushButton; +class TQListViewItem; + +class PhraseLV; + +class PhraseBookBox : public TQDialog +{ + Q_OBJECT +public: + PhraseBookBox( const TQString& filename, const PhraseBook& phraseBook, + TQWidget *parent = 0, const char *name = 0, + bool modal = FALSE ); + + const PhraseBook& phraseBook() const { return pb; } + +protected: + virtual void keyPressEvent( TQKeyEvent *ev ); + +private slots: + void newPhrase(); + void removePhrase(); + void save(); + void sourceChanged( const TQString& source ); + void targetChanged( const TQString& target ); + void definitionChanged( const TQString& definition ); + void selectionChanged( TQListViewItem *item ); + +private: + void selectItem( TQListViewItem *item ); + void enableDisable(); + + TQLineEdit *sourceLed; + TQLineEdit *targetLed; + TQLineEdit *definitionLed; + TQPushButton *newBut; + TQPushButton *removeBut; + PhraseLV *lv; + TQString fn; + PhraseBook pb; +}; + +#endif diff --git a/tools/linguist/linguist/phraselv.cpp b/tools/linguist/linguist/phraselv.cpp new file mode 100644 index 000000000..831240e4d --- /dev/null +++ b/tools/linguist/linguist/phraselv.cpp @@ -0,0 +1,171 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +/* TRANSLATOR PhraseLV + + The phrase list in the right panel of the main window (with Source phrase, + Target phrase, and Definition in its header) is a PhraseLV object. +*/ + +#include "phraselv.h" + +#include +#include +#include + +class WhatPhrase : public TQWhatsThis +{ +public: + WhatPhrase( PhraseLV *w ); + + virtual TQString text( const TQPoint& p ); + +private: + PhraseLV *parent; +}; + +WhatPhrase::WhatPhrase( PhraseLV *w ) + : TQWhatsThis( w ) +{ + parent = w; +} + +TQString WhatPhrase::text( const TQPoint& p ) +{ + TQListViewItem *item = parent->itemAt( p ); + if ( item == 0 ) + return PhraseLV::tr( "This is a list of phrase entries relevant to the" + " source text. Each phrase is supplemented with a suggested" + " translation and a definition." ); + else + return TQString( PhraseLV::tr("

%1:  %2

" + "

%3:  %4

" + "

%5:  %6

") ) + .arg( parent->columnText(PhraseLVI::SourceTextShown) ) + .arg( item->text(PhraseLVI::SourceTextShown) ) + .arg( parent->columnText(PhraseLVI::TargetTextShown) ) + .arg( item->text(PhraseLVI::TargetTextShown) ) + .arg( parent->columnText(PhraseLVI::DefinitionText) ) + .arg( item->text(PhraseLVI::DefinitionText) ); +} + +PhraseLVI::PhraseLVI( PhraseLV *parent, const Phrase& phrase, int accelKey ) + : TQListViewItem( parent ), + akey( accelKey ) +{ + setPhrase( phrase ); +} + +TQString PhraseLVI::key( int column, bool ascending ) const +{ + if ( column == SourceTextShown ) { + if ( sourceTextKey.isEmpty() ) { + if ( ascending ) { + return ""; + } else { + return TQString::null; + } + } else { + return sourceTextKey; + } + } else if ( column == TargetTextShown ) { + return targetTextKey; + } else { + return TQChar( '0' + akey ) + text( column ); + } +} + +void PhraseLVI::setText( int column, const TQString& text ) +{ + if ( column == SourceTextShown ) { + sourceTextKey = makeKey( text ); + } else if ( column == TargetTextShown ) { + targetTextKey = makeKey( text ); + } + TQListViewItem::setText( column, text ); +} + +void PhraseLVI::setPhrase( const Phrase& phrase ) +{ + setText( SourceTextShown, phrase.source().simplifyWhiteSpace() ); + setText( TargetTextShown, phrase.target().simplifyWhiteSpace() ); + setText( DefinitionText, phrase.definition() ); + setText( SourceTextOriginal, phrase.source() ); + setText( TargetTextOriginal, phrase.target() ); +} + +Phrase PhraseLVI::phrase() const +{ + return Phrase( text(SourceTextOriginal), text(TargetTextOriginal), + text(DefinitionText) ); +} + +TQString PhraseLVI::makeKey( const TQString& text ) const +{ + if ( text == NewPhrase ) + return TQString::null; + + TQString key; + for ( int i = 0; i < (int) text.length(); i++ ) { + if ( text[i] != TQChar('&') ) + key += text[i].lower(); + } + // see Section 5, Exercise 4 of The Art of Computer Programming + key += TQChar::null; + key += text; + return key; +} + +PhraseLV::PhraseLV( TQWidget *parent, const char *name ) + : TQListView( parent, name ) +{ + setAllColumnsShowFocus( TRUE ); + setShowSortIndicator( TRUE ); + for ( int i = 0; i < 3; i++ ) + addColumn( TQString::null, 120 ); + setColumnText( PhraseLVI::SourceTextShown, tr("Source phrase") ); + setColumnText( PhraseLVI::TargetTextShown, tr("Translation") ); + setColumnText( PhraseLVI::DefinitionText, tr("Definition") ); + header()->setStretchEnabled( TRUE, -1 ); + what = new WhatPhrase( this ); +} + +PhraseLV::~PhraseLV() +{ +// delete what; +} + +TQSize PhraseLV::sizeHint() const +{ + return TQSize( TQListView::sizeHint().width(), 50 ); +} diff --git a/tools/linguist/linguist/phraselv.h b/tools/linguist/linguist/phraselv.h new file mode 100644 index 000000000..f44697e41 --- /dev/null +++ b/tools/linguist/linguist/phraselv.h @@ -0,0 +1,83 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef PHRASELV_H +#define PHRASELV_H + +#include "phrase.h" + +#include + +class TQWhatsThis; + +class PhraseLV; + +#define NewPhrase PhraseLV::tr( "(New Phrase)" ) + +class PhraseLVI : public TQListViewItem +{ +public: + enum { SourceTextShown, TargetTextShown, DefinitionText, SourceTextOriginal, + TargetTextOriginal }; + + PhraseLVI( PhraseLV *parent, const Phrase& phrase, int accelKey = 0 ); + + virtual void setText( int column, const TQString& text ); + virtual TQString key( int column, bool ascending ) const; + + void setPhrase( const Phrase& phrase ); + Phrase phrase() const; + int accelKey() const { return akey; } + +private: + TQString makeKey( const TQString& text ) const; + + int akey; + TQString sourceTextKey; + TQString targetTextKey; +}; + +class PhraseLV : public TQListView +{ + Q_OBJECT +public: + PhraseLV( TQWidget *parent, const char *name ); + ~PhraseLV(); + + virtual TQSize sizeHint() const; + +private: + TQWhatsThis *what; +}; + +#endif diff --git a/tools/linguist/linguist/printout.cpp b/tools/linguist/linguist/printout.cpp new file mode 100644 index 000000000..c0f1e94f9 --- /dev/null +++ b/tools/linguist/linguist/printout.cpp @@ -0,0 +1,182 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "printout.h" + +#include +#include + +PrintOut::PrintOut( TQPrinter *printer ) + : pr( printer ), pdmetrics( printer ), nextRule( NoRule ), page( 0 ) +{ + p.begin( pr ); + TQFont f( "Arial" ); + f8 = f; + f8.setPointSize( 8 ); + f10 = f; + f10.setPointSize( 10 ); + p.setFont( f10 ); + fmetrics = new TQFontMetrics( p.fontMetrics() ); + hmargin = 5 * pdmetrics.width() / pdmetrics.widthMM(); // 5 mm + vmargin = 5 * pdmetrics.height() / pdmetrics.heightMM(); // 5 mm + hsize = pdmetrics.width() - 2 * hmargin; + vsize = pdmetrics.height() - vmargin; + dateTime = TQDateTime::currentDateTime(); + breakPage(); + vsize -= voffset; + cp = Paragraph( TQPoint(hmargin, voffset) ); +} + +PrintOut::~PrintOut() +{ + flushLine(); + delete fmetrics; + p.end(); +} + +void PrintOut::setRule( Rule rule ) +{ + if ( (int) nextRule < (int) rule ) + nextRule = rule; +} + +void PrintOut::setGuide( const TQString& guide ) +{ + g = guide; +} + +void PrintOut::vskip() +{ + if ( !firstParagraph ) + voffset += 14; +} + +void PrintOut::flushLine( bool /* mayBreak */ ) +{ + if ( voffset + cp.rect.height() > vsize ) + breakPage(); + else if ( !firstParagraph ) + drawRule( nextRule ); + + for ( int i = 0; i < (int) cp.boxes.count(); i++ ) { + Box b = cp.boxes[i]; + b.rect.moveBy( 0, voffset ); + TQRect r = b.rect; + p.setFont( b.font ); + p.drawText( r, b.align, b.text ); + } + voffset += cp.rect.height(); + + nextRule = NoRule; + cp = Paragraph( TQPoint(hmargin, voffset) ); + firstParagraph = FALSE; +} + +void PrintOut::addBox( int percent, const TQString& text, Style style, + int halign ) +{ + int align = halign | TQt::AlignTop; + TQFont f = f10; + if ( style == Strong ) + f.setBold( TRUE ); + else if ( style == Emphasis ) + f.setItalic( TRUE ); + int wd = hsize * percent / 100; + TQRect r( cp.rect.x() + cp.rect.width(), 0, wd, vsize ); + int ht = p.boundingRect( r, align, text ).height(); + + Box b( r, text, f, align ); + cp.boxes.append( b ); + cp.rect.setSize( TQSize(cp.rect.width() + wd, TQMAX(cp.rect.height(), ht)) ); +} + +void PrintOut::breakPage() +{ + static const int LeftAlign = TQt::AlignLeft | TQt::AlignTop; + static const int RightAlign = TQt::AlignRight | TQt::AlignTop; + TQRect r1, r2; + int h1 = 0; + int h2 = 0; + + if ( page++ > 0 ) + pr->newPage(); + voffset = 0; + + p.setFont( f10 ); + r1 = TQRect( hmargin, voffset, 3 * hsize / 4, vsize ); + r2 = TQRect( r1.x() + r1.width(), voffset, hsize - r1.width(), vsize ); + h1 = p.boundingRect( r1, LeftAlign, pr->docName() ).height(); + p.drawText( r1, LeftAlign, pr->docName() ); + h2 = p.boundingRect( r2, RightAlign, TQString::number(page) ).height(); + p.drawText( r2, RightAlign, TQString::number(page) ); + voffset += TQMAX( h1, h2 ); + + r1 = TQRect( hmargin, voffset, hsize / 2, LeftAlign ); + p.setFont( f8 ); + h1 = p.boundingRect( r1, LeftAlign, dateTime.toString() ).height(); + p.drawText( r1, LeftAlign, dateTime.toString() ); + p.setFont( f10 ); + voffset += TQMAX( h1, h2 ); + + voffset += 4; + p.drawLine( TQPoint(hmargin, voffset), TQPoint(hmargin + hsize, voffset) ); + voffset += 14; + firstParagraph = TRUE; +} + +void PrintOut::drawRule( Rule rule ) +{ + TQPen pen; + + switch ( rule ) { + case NoRule: + voffset += 5; + break; + case ThinRule: + pen.setColor( TQColor(192, 192, 192) ); + pen.setStyle( TQPen::DotLine ); + pen.setWidth( 0 ); + p.setPen( pen ); + voffset += 5; + p.drawLine( TQPoint(hmargin, voffset), + TQPoint(hmargin + hsize, voffset) ); + p.setPen( TQPen() ); + voffset += 2; + break; + case ThickRule: + voffset += 7; + p.drawLine( TQPoint(hmargin, voffset), + TQPoint(hmargin + hsize, voffset) ); + voffset += 4; + } +} diff --git a/tools/linguist/linguist/printout.h b/tools/linguist/linguist/printout.h new file mode 100644 index 000000000..639d35caa --- /dev/null +++ b/tools/linguist/linguist/printout.h @@ -0,0 +1,126 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef PRINTOUT_H +#define PRINTOUT_H + +#include +#include +#include +#include +#include +#include + +class TQPrinter; +class TQFontMetrics; + +class PrintOut +{ +public: + enum Rule { NoRule, ThinRule, ThickRule }; + enum Style { Normal, Strong, Emphasis }; + + PrintOut( TQPrinter *printer ); + ~PrintOut(); + + void setRule( Rule rule ); + void setGuide( const TQString& guide ); + void vskip(); + void flushLine( bool mayBreak = FALSE ); + void addBox( int percent, const TQString& text = TQString::null, + Style style = Normal, + int halign = TQt::AlignLeft | TQt::WordBreak ); + + int pageNum() const { return page; } + + struct Box + { + TQRect rect; + TQString text; + TQFont font; + int align; + + Box() : align( 0 ) { } + Box( const TQRect& r, const TQString& t, const TQFont& f, int a ) + : rect( r ), text( t ), font( f ), align( a ) { } + Box( const Box& b ) + : rect( b.rect ), text( b.text ), font( b.font ), + align( b.align ) { } + + Box& operator=( const Box& b ) { + rect = b.rect; + text = b.text; + font = b.font; + align = b.align; + return *this; + } + + bool operator==( const Box& b ) const { + return rect == b.rect && text == b.text && font == b.font && + align == b.align; + } + }; + +private: + void breakPage(); + void drawRule( Rule rule ); + + struct Paragraph { + TQRect rect; + TQValueList boxes; + + Paragraph() { } + Paragraph( TQPoint p ) : rect( p, TQSize(0, 0) ) { } + }; + + TQPrinter *pr; + TQPainter p; + TQFont f8; + TQFont f10; + TQFontMetrics *fmetrics; + TQPaintDeviceMetrics pdmetrics; + Rule nextRule; + Paragraph cp; + int page; + bool firstParagraph; + TQString g; + TQDateTime dateTime; + + int hmargin; + int vmargin; + int voffset; + int hsize; + int vsize; +}; + +#endif diff --git a/tools/linguist/linguist/simtexth.cpp b/tools/linguist/linguist/simtexth.cpp new file mode 100644 index 000000000..56e868246 --- /dev/null +++ b/tools/linguist/linguist/simtexth.cpp @@ -0,0 +1,239 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "simtexth.h" + +#include + +#include +#include +#include +#include +#include +#include + +#include + +typedef TQValueList TML; + +/* + How similar are two texts? The approach used here relies on co-occurrence + matrices and is very efficient. + + Let's see with an example: how similar are "here" and "hither"? The + co-occurrence matrix M for "here" is M[h,e] = 1, M[e,r] = 1, M[r,e] = 1, and 0 + elsewhere; the matrix N for "hither" is N[h,i] = 1, N[i,t] = 1, ..., + N[h,e] = 1, N[e,r] = 1, and 0 elsewhere. The union U of both matrices is the + matrix U[i,j] = max { M[i,j], N[i,j] }, and the intersection V is + V[i,j] = min { M[i,j], N[i,j] }. The score for a pair of texts is + + score = (sum of V[i,j] over all i, j) / (sum of U[i,j] over all i, j), + + a formula suggested by Arnt Gulbrandsen. Here we have + + score = 2 / 6, + + or one third. + + The implementation differs from this in a few details. Most importantly, + repetitions are ignored; for input "xxx", M[x,x] equals 1, not 2. +*/ + +/* + Every character is assigned to one of 20 buckets so that the co-occurrence + matrix retquires only 20 * 20 = 400 bits, not 256 * 256 = 65536 bits or even + more if we want the whole Unicode. Which character falls in which bucket is + arbitrary. + + The second half of the table is a replica of the first half, because of + laziness. +*/ +static const int indexOf[256] = { + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +// ! " # $ % & ' ( ) * + , - . / + 0, 2, 6, 7, 10, 12, 15, 19, 2, 6, 7, 10, 12, 15, 19, 0, +// 0 1 2 3 4 5 6 7 8 9 : ; < = > ? + 1, 3, 4, 5, 8, 9, 11, 13, 14, 16, 2, 6, 7, 10, 12, 15, +// @ A B C D E F G H I J K L M N O + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 6, 10, 11, 12, 13, 14, +// P Q R S T U V W X Y Z [ \ ] ^ _ + 15, 12, 16, 17, 18, 19, 2, 10, 15, 7, 19, 2, 6, 7, 10, 0, +// ` a b c d e f g h i j k l m n o + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 6, 10, 11, 12, 13, 14, +// p q r s t u v w x y z { | } ~ + 15, 12, 16, 17, 18, 19, 2, 10, 15, 7, 19, 2, 6, 7, 10, 0, + + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 2, 6, 7, 10, 12, 15, 19, 2, 6, 7, 10, 12, 15, 19, 0, + 1, 3, 4, 5, 8, 9, 11, 13, 14, 16, 2, 6, 7, 10, 12, 15, + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 6, 10, 11, 12, 13, 14, + 15, 12, 16, 17, 18, 19, 2, 10, 15, 7, 19, 2, 6, 7, 10, 0, + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 6, 10, 11, 12, 13, 14, + 15, 12, 16, 17, 18, 19, 2, 10, 15, 7, 19, 2, 6, 7, 10, 0 +}; + +/* + The entry bitCount[i] (for i between 0 and 255) is the number of bits used to + represent i in binary. +*/ +static const int bitCount[256] = { + 0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4, + 1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5, + 1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, + 1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, + 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, + 3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, + 3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, + 4, 5, 5, 6, 5, 6, 6, 7, 5, 6, 6, 7, 6, 7, 7, 8 +}; + +struct CoMatrix +{ + /* + The matrix has 20 * 20 = 400 entries. This retquires 50 bytes, or 13 + words. Some operations are performed on words for more efficiency. + */ + union { + Q_UINT8 b[52]; + Q_UINT32 w[13]; + }; + + CoMatrix() { memset( b, 0, 52 ); } + CoMatrix( const char *text ) { + char c = '\0', d; + memset( b, 0, 52 ); + /* + The Knuth books are not in the office only for show; they help make + loops 30% faster and 20% as readable. + */ + while ( (d = *text) != '\0' ) { + setCoocc( c, d ); + if ( (c = *++text) != '\0' ) { + setCoocc( d, c ); + text++; + } + } + } + + void setCoocc( char c, char d ) { + int k = indexOf[(uchar) c] + 20 * indexOf[(uchar) d]; + b[k >> 3] |= k & 0x7; + } + + int worth() const { + int w = 0; + for ( int i = 0; i < 50; i++ ) + w += bitCount[b[i]]; + return w; + } +}; + +static inline CoMatrix reunion( const CoMatrix& m, const CoMatrix& n ) +{ + CoMatrix p; + for ( int i = 0; i < 13; i++ ) + p.w[i] = m.w[i] | n.w[i]; + return p; +} + +static inline CoMatrix intersection( const CoMatrix& m, const CoMatrix& n ) +{ + CoMatrix p; + for ( int i = 0; i < 13; i++ ) + p.w[i] = m.w[i] & n.w[i]; + return p; +} + +CandidateList similarTextHeuristicCandidates( const MetaTranslator *tor, + const char *text, + int maxCandidates ) +{ + TQValueList scores; + CandidateList candidates; + CoMatrix cmTarget( text ); + int targetLen = qstrlen( text ); + + TML all = tor->translatedMessages(); + TML::Iterator it; + + for ( it = all.begin(); it != all.end(); ++it ) { + if ( (*it).type() == MetaTranslatorMessage::Unfinished || + (*it).translation().isEmpty() ) + continue; + + TQString s = tor->toUnicode( (*it).sourceText(), (*it).utf8() ); + CoMatrix cm( s.latin1() ); + int delta = TQABS( (int) s.length() - targetLen ); + + /* + Here is the score formula. A comment above contains a + discussion on a similar (but simpler) formula. + */ + int score = ( (intersection(cm, cmTarget).worth() + 1) << 10 ) / + ( reunion(cm, cmTarget).worth() + (delta << 1) + 1 ); + + if ( (int) candidates.count() == maxCandidates && + score > scores[maxCandidates - 1] ) + candidates.remove( candidates.last() ); + if ( (int) candidates.count() < maxCandidates && score >= 190 ) { + Candidate cand( s, (*it).translation() ); + + int i; + for ( i = 0; i < (int) candidates.count(); i++ ) { + if ( score >= scores[i] ) { + if ( score == scores[i] ) { + if ( candidates[i] == cand ) + goto continue_outer_loop; + } else { + break; + } + } + } + scores.insert( scores.at(i), score ); + candidates.insert( candidates.at(i), cand ); + } + continue_outer_loop: + ; + } + return candidates; +} diff --git a/tools/linguist/linguist/simtexth.h b/tools/linguist/linguist/simtexth.h new file mode 100644 index 000000000..0e54800ab --- /dev/null +++ b/tools/linguist/linguist/simtexth.h @@ -0,0 +1,64 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef SIMTEXTH_H +#define SIMTEXTH_H + +#include +#include + +class MetaTranslator; + +struct Candidate { + TQString source; + TQString target; + + Candidate() { } + Candidate( const TQString& source0, const TQString& target0 ) + : source( source0 ), target( target0 ) { } +}; + +inline bool operator==( const Candidate& c, const Candidate& d ) { + return c.target == d.target && c.source == d.source; +} +inline bool operator!=( const Candidate& c, const Candidate& d ) { + return !operator==( c, d ); +} + +typedef TQValueList CandidateList; + +CandidateList similarTextHeuristicCandidates( const MetaTranslator *tor, + const char *text, + int maxCandidates ); + +#endif diff --git a/tools/linguist/linguist/statistics.ui b/tools/linguist/linguist/statistics.ui new file mode 100644 index 000000000..257d4a423 --- /dev/null +++ b/tools/linguist/linguist/statistics.ui @@ -0,0 +1,259 @@ + +Statistics +********************************************************************* +** Copyright (C) 2002-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +********************************************************************* + + + Statistics + + + + 0 + 0 + 336 + 164 + + + + Statistics + + + + unnamed + + + + layout2 + + + + unnamed + + + + spacer4_2 + + + Horizontal + + + Expanding + + + + 40 + 20 + + + + + + closeBtn + + + &Close + + + + + spacer4 + + + Horizontal + + + Expanding + + + + 40 + 20 + + + + + + + + frame4 + + + GroupBoxPanel + + + Raised + + + + unnamed + + + + textLabel4 + + + Translation + + + AlignVCenter|AlignRight + + + + + textLabel5 + + + Source + + + AlignVCenter|AlignRight + + + + + untrWords + + + 0 + + + AlignVCenter|AlignRight + + + + + trWords + + + 0 + + + AlignVCenter|AlignRight + + + + + textLabel1 + + + Words: + + + + + trChars + + + 0 + + + AlignVCenter|AlignRight + + + + + untrChars + + + 0 + + + AlignVCenter|AlignRight + + + + + textLabel3 + + + Characters: + + + + + textLabel6 + + + Characters (with spaces): + + + + + trCharsSpc + + + 0 + + + AlignVCenter|AlignRight + + + + + untrCharsSpc + + + 0 + + + AlignVCenter|AlignRight + + + + + + + + + closeBtn + clicked() + Statistics + close() + + + + statistics.ui.h + + + closed() + + + updateStats( int w1, int c1, int cs1, int w2, int c2, int cs2 ) + closeEvent( TQCloseEvent * e ) + + + init() + + + + diff --git a/tools/linguist/linguist/statistics.ui.h b/tools/linguist/linguist/statistics.ui.h new file mode 100644 index 000000000..a100a78b8 --- /dev/null +++ b/tools/linguist/linguist/statistics.ui.h @@ -0,0 +1,53 @@ +/********************************************************************** +** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +void Statistics::init() +{ + setFixedHeight( sizeHint().height() ); +} + +void Statistics::updateStats( int w1, int c1, int cs1, int w2, int c2, int cs2 ) +{ + untrWords->setText( TQString::number( w1 ) ); + untrChars->setText( TQString::number( c1 ) ); + untrCharsSpc->setText( TQString::number( cs1 ) ); + trWords->setText( TQString::number( w2 ) ); + trChars->setText( TQString::number( c2 ) ); + trCharsSpc->setText( TQString::number( cs2 ) ); +} + +void Statistics::closeEvent( TQCloseEvent * e ) +{ + emit closed(); + TQDialog::closeEvent( e ); +} diff --git a/tools/linguist/linguist/trwindow.cpp b/tools/linguist/linguist/trwindow.cpp new file mode 100644 index 000000000..35b95b7a8 --- /dev/null +++ b/tools/linguist/linguist/trwindow.cpp @@ -0,0 +1,2071 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +/* TRANSLATOR TrWindow + + This is the application's main window. +*/ + +#include "trwindow.h" +#include "listviews.h" +#include "finddialog.h" +#include "msgedit.h" +#include "phrasebookbox.h" +#include "printout.h" +#include "about.h" +#include "phraselv.h" +#include "statistics.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#define pagecurl_mask_width 53 +#define pagecurl_mask_height 51 +static const uchar pagecurl_mask_bits[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0x0f, 0x80, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0x00, 0xfe, 0xff, + 0xff, 0xff, 0xff, 0x0f, 0x00, 0xf0, 0xff, 0xff, 0xff, 0xff, 0x0f, 0x00, + 0xc0, 0xff, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x80, 0xff, 0xff, 0xff, 0xff, + 0x0f, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xfe, 0xff, + 0xff, 0xff, 0x0f, 0x00, 0x00, 0xfc, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, + 0xfc, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xf8, 0xff, 0xff, 0xff, 0x0f, + 0x00, 0x00, 0xf0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xf0, 0xff, 0xff, + 0xff, 0x0f, 0x00, 0x00, 0xf0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xf0, + 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, + 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, + 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, + 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, + 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, + 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, + 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, + 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, + 0x00, 0xe0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0xc0, 0xff, 0xff, 0xff, + 0x0f, 0x00, 0x00, 0xc0, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0x00, 0xfc, + 0xff, 0xff, 0x0f, 0x00, 0x00, 0x00, 0x00, 0xf8, 0xff, 0x0f, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xfc, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x0f, + 0x00, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, + 0xe0, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x0f, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08 }; + +typedef TQValueList TML; + +static const int ErrorMS = 600000; // for error messages +static const int MessageMS = 2500; + +TQPixmap * TrWindow::pxOn = 0; +TQPixmap * TrWindow::pxOff = 0; +TQPixmap * TrWindow::pxObsolete = 0; +TQPixmap * TrWindow::pxDanger = 0; + +enum Ending { End_None, End_FullStop, End_Interrobang, End_Colon, + End_Ellipsis }; + +static Ending ending( TQString str ) +{ + str = str.simplifyWhiteSpace(); + int ch = 0; + if ( !str.isEmpty() ) + ch = str.right( 1 )[0].unicode(); + + switch ( ch ) { + case 0x002e: // full stop + if ( str.endsWith(TQString("...")) ) + return End_Ellipsis; + else + return End_FullStop; + case 0x0589: // armenian full stop + case 0x06d4: // arabic full stop + case 0x3002: // ideographic full stop + return End_FullStop; + case 0x0021: // exclamation mark + case 0x003f: // question mark + case 0x00a1: // inverted exclamation mark + case 0x00bf: // inverted question mark + case 0x01c3: // latin letter retroflex click + case 0x037e: // greek question mark + case 0x061f: // arabic question mark + case 0x203c: // double exclamation mark + case 0x203d: // interrobang + case 0x2048: // question exclamation mark + case 0x2049: // exclamation question mark + case 0x2762: // heavy exclamation mark ornament + return End_Interrobang; + case 0x003a: // colon + return End_Colon; + case 0x2026: // horizontal ellipsis + return End_Ellipsis; + default: + return End_None; + } +} + +class Action : public TQAction +{ +public: + Action( TQPopupMenu *pop, const TQString& menuText, TQObject *receiver, + const char *member, const TQString &imageName = TQString::null, + int accel = 0, bool toggle = FALSE ); + Action( TQPopupMenu *pop, const TQString& menuText, int accel = 0, + bool toggle = FALSE ); + + virtual void setWhatsThis( const TQString& whatsThis ); + + bool addToToolbar( TQToolBar *tb, const TQString& text ); +}; + +Action::Action( TQPopupMenu *pop, const TQString& menuText, TQObject *receiver, + const char *member, const TQString &imageName, int accel, + bool toggle ) + : TQAction( pop->parent(), (const char *) 0, toggle ) +{ + setMenuText( menuText ); + setAccel( accel ); + + if ( !imageName.isEmpty() ) { + TQPixmap enabledPix = TQPixmap::fromMimeSource( imageName ); + TQIconSet s( enabledPix ); + if ( imageName != "whatsthis.xpm" ) { + TQPixmap disabledPix = TQPixmap::fromMimeSource( "d_" + imageName ); + s.setPixmap( disabledPix, TQIconSet::Small, TQIconSet::Disabled ); + } + setIconSet( s ); + } + TQAction::addTo( pop ); + connect( this, SIGNAL(activated()), receiver, member ); +} + +Action::Action( TQPopupMenu *pop, const TQString& menuText, int accel, + bool toggle ) + : TQAction( pop->parent(), (const char *) 0, toggle ) +{ + TQAction::addTo( pop ); + setMenuText( menuText ); + setAccel( accel ); +} + +void Action::setWhatsThis( const TQString& whatsThis ) +{ + TQAction::setWhatsThis( whatsThis ); + setStatusTip( whatsThis ); +} + +bool Action::addToToolbar( TQToolBar *tb, const TQString& text ) +{ + setText( text ); + return TQAction::addTo( tb ); +} + +const TQPixmap TrWindow::pageCurl() +{ + TQPixmap pixmap; + pixmap = TQPixmap::fromMimeSource( "pagecurl.png" ); + if ( !pixmap.isNull() ) { + TQBitmap pageCurlMask( pagecurl_mask_width, pagecurl_mask_height, + pagecurl_mask_bits, TRUE ); + pixmap.setMask( pageCurlMask ); + } + + return pixmap; +} + +TrWindow::TrWindow() + : TQMainWindow( 0, "translation window", WType_TopLevel | WDestructiveClose ) +{ + +#ifndef Q_WS_MACX + setIcon( TQPixmap::fromMimeSource( "appicon.png" ) ); +#endif + + // Create the application global listview symbols + pxOn = new TQPixmap( TQPixmap::fromMimeSource( "s_check_on.png" ) ); + pxOff = new TQPixmap( TQPixmap::fromMimeSource( "s_check_off.png" ) ); + pxObsolete = new TQPixmap( TQPixmap::fromMimeSource( "d_s_check_obs.png" ) ); + pxDanger = new TQPixmap( TQPixmap::fromMimeSource( "s_check_danger.png" ) ); + + // Set up the Scope dock window + TQDockWindow * dwScope = new TQDockWindow( TQDockWindow::InDock, this, + "context"); + dwScope->setResizeEnabled( TRUE ); + dwScope->setCloseMode( TQDockWindow::Always ); + addDockWindow( dwScope, tr("Context"), TQt::DockLeft ); + dwScope->setCaption( tr("Context") ); + dwScope->setFixedExtentWidth( 200 ); + lv = new TQListView( dwScope, "context list view" ); + lv->setShowSortIndicator( TRUE ); + lv->setAllColumnsShowFocus( TRUE ); + lv->header()->setStretchEnabled( TRUE, 1 ); + TQFontMetrics fm( font() ); + lv->addColumn( tr("Done"), fm.width( tr("Done") ) + 10 ); + lv->addColumn( tr("Context") ); + lv->addColumn( tr("Items"), 55 ); + lv->setColumnAlignment( 0, TQt::AlignCenter ); + lv->setColumnAlignment( 2, TQt::AlignRight ); + lv->setSorting( 0 ); + lv->setHScrollBarMode( TQScrollView::AlwaysOff ); + dwScope->setWidget( lv ); + + messageIsShown = FALSE; + me = new MessageEditor( &tor, this, "message editor" ); + setCentralWidget( me ); + slv = me->sourceTextList(); + plv = me->phraseList(); + + setupMenuBar(); + setupToolBars(); + + progress = new TQLabel( statusBar(), "progress" ); + statusBar()->addWidget( progress, 0, TRUE ); + modified = new TQLabel( TQString(" %1 ").arg(tr("MOD")), statusBar(), + "modified?" ); + statusBar()->addWidget( modified, 0, TRUE ); + + dirtyItem = -1; + numFinished = 0; + numNonobsolete = 0; + numMessages = 0; + updateProgress(); + + dirty = FALSE; + updateCaption(); + + phraseBooks.setAutoDelete( TRUE ); + + f = new FindDialog( FALSE, this, "find", FALSE ); + f->setCaption( tr("TQt Linguist") ); + h = new FindDialog( TRUE, this, "replace", FALSE ); + h->setCaption( tr("TQt Linguist") ); + findMatchCase = FALSE; + findWhere = 0; + foundItem = 0; + foundScope = 0; + foundWhere = 0; + foundOffset = 0; + + connect( lv, SIGNAL(selectionChanged(TQListViewItem *)), + this, SLOT(showNewScope(TQListViewItem *)) ); + + connect( slv, SIGNAL(currentChanged(TQListViewItem *)), + this, SLOT(showNewCurrent(TQListViewItem *)) ); + + connect( slv, SIGNAL(clicked(TQListViewItem *, const TQPoint&, int)), + this, SLOT(showNewCurrent(TQListViewItem *)) ); + + connect( slv, SIGNAL(clicked(TQListViewItem *, const TQPoint&, int)), + this, SLOT(toggleFinished(TQListViewItem *, const TQPoint&, int)) ); + + connect( me, SIGNAL(translationChanged(const TQString&)), + this, SLOT(updateTranslation(const TQString&)) ); + connect( me, SIGNAL(finished(bool)), this, SLOT(updateFinished(bool)) ); + connect( me, SIGNAL(prevUnfinished()), this, SLOT(prevUnfinished()) ); + connect( me, SIGNAL(nextUnfinished()), this, SLOT(nextUnfinished()) ); + connect( me, SIGNAL(focusSourceList()), this, SLOT(focusSourceList()) ); + connect( me, SIGNAL(focusPhraseList()), this, SLOT(focusPhraseList()) ); + connect( f, SIGNAL(findNext(const TQString&, int, bool)), + this, SLOT(findNext(const TQString&, int, bool)) ); + + TQWhatsThis::add( lv, tr("This panel lists the source contexts.") ); + + TQWhatsThis::add( slv, tr("This panel lists the source texts. " + "Items that violate validation rules " + "are marked with a warning.") ); + showNewCurrent( 0 ); + + TQSize as( qApp->desktop()->size() ); + as -= TQSize( 30, 30 ); + resize( TQSize( 1000, 800 ).boundedTo( as ) ); + readConfig(); + stats = 0; + srcWords = 0; + srcChars = 0; + srcCharsSpc = 0; +} + +TrWindow::~TrWindow() +{ + writeConfig(); + delete stats; +} + +void TrWindow::openFile( const TQString& name ) +{ + if ( !name.isEmpty() ) { + statusBar()->message( tr("Loading...") ); + qApp->processEvents(); + tor.clear(); + if ( tor.load(name) ) { + slv->clear(); + slv->repaint(); + slv->viewport()->repaint(); + slv->setUpdatesEnabled( FALSE ); + slv->viewport()->setUpdatesEnabled( FALSE ); + lv->clear(); + lv->repaint(); + lv->viewport()->repaint(); + lv->setUpdatesEnabled( FALSE ); + lv->viewport()->setUpdatesEnabled( FALSE ); + setEnabled( FALSE ); + numFinished = 0; + numNonobsolete = 0; + numMessages = 0; + foundScope = 0; + + TML all = tor.messages(); + TML::Iterator it; + TQDict contexts( 1009 ); + + srcWords = 0; + srcChars = 0; + srcCharsSpc = 0; + for ( it = all.begin(); it != all.end(); ++it ) { + qApp->processEvents(); + ContextLVI *c = contexts.find( TQString((*it).context()) ); + if ( c == 0 ) { + c = new ContextLVI( lv, tor.toUnicode((*it).context(), + (*it).utf8()) ); + contexts.insert( TQString((*it).context()), c ); + } + if ( TQCString((*it).sourceText()) == ContextComment ) { + c->appendToComment( tor.toUnicode((*it).comment(), + (*it).utf8()) ); + } else { + MessageLVI * tmp = new MessageLVI( slv, *it, + tor.toUnicode((*it).sourceText(), + (*it).utf8()), + tor.toUnicode((*it).comment(), + (*it).utf8()), c ); + tmp->setDanger( danger(tmp->sourceText(), + tmp->translation()) && + tmp->message().type() == + MetaTranslatorMessage::Finished ); + c->instantiateMessageItem( slv, tmp ); + if ( (*it).type() != MetaTranslatorMessage::Obsolete ) { + numNonobsolete++; + if ( (*it).type() == MetaTranslatorMessage::Finished ) + numFinished++; + doCharCounting( tmp->sourceText(), srcWords, srcChars, srcCharsSpc ); + } else { + c->incrementObsoleteCount(); + } + numMessages++; + } + c->updateStatus(); + } + slv->viewport()->setUpdatesEnabled( TRUE ); + slv->setUpdatesEnabled( TRUE ); + lv->viewport()->setUpdatesEnabled( TRUE ); + lv->setUpdatesEnabled( TRUE ); + setEnabled( TRUE ); + slv->repaint(); + slv->viewport()->repaint(); + lv->triggerUpdate(); + updateProgress(); + filename = name; + dirty = FALSE; + updateCaption(); + me->showNothing(); + doneAndNextAct->setEnabled( FALSE ); + doneAndNextAlt->setEnabled( FALSE ); + messageIsShown = FALSE; + statusBar()->message( + tr("%1 source phrase(s) loaded.").arg(numMessages), + MessageMS ); + + foundItem = 0; + foundWhere = 0; + foundOffset = 0; + if ( lv->childCount() > 0 ) { + findAct->setEnabled( TRUE ); + findAgainAct->setEnabled( FALSE ); +#ifdef notyet + replaceAct->setEnabled( TRUE ); +#endif + lv->setCurrentItem( lv->firstChild() ); + } + addRecentlyOpenedFile( name, recentFiles ); + updateStatistics(); + } else { + statusBar()->clear(); + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("Cannot open '%1'.").arg(name) ); + } + } +} + +void TrWindow::open() +{ + if ( maybeSave() ) { + TQString newFilename = TQFileDialog::getOpenFileName( filename, + tr("TQt translation source (*.ts)\n" + "All files (*)"), + this, "open" ); + openFile( newFilename ); + } +} + +void TrWindow::save() +{ + if ( filename.isEmpty() ) + return; + + if ( tor.save(filename) ) { + dirty = FALSE; + updateCaption(); + statusBar()->message( tr("File saved."), MessageMS ); + } else { + TQMessageBox::warning( this, tr("TQt Linguist"), tr("Cannot save '%1'.") + .arg(filename) ); + } +} + +void TrWindow::saveAs() +{ + TQString newFilename = TQFileDialog::getSaveFileName( filename, + tr( "TQt translation source (*.ts)\n" + "All files (*)"), + this, "save_as" ); + if ( !newFilename.isEmpty() ) { + filename = newFilename; + save(); + updateCaption(); + } +} + +void TrWindow::release() +{ + TQString newFilename = filename; + newFilename.replace( TQRegExp(".ts$"), "" ); + newFilename += TQString( ".qm" ); + + newFilename = TQFileDialog::getSaveFileName( newFilename, + tr("TQt message files for released applications (*.qm)\n" + "All files (*)"), + this, "release", + tr("Release") ); + if ( !newFilename.isEmpty() ) { + if ( tor.release(newFilename) ) + statusBar()->message( tr("File created."), MessageMS ); + else + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("Cannot save '%1'.").arg(newFilename) ); + } +} + +void TrWindow::print() +{ + int pageNum = 0; + + if ( printer.setup(this) ) { + TQApplication::setOverrideCursor( WaitCursor ); + printer.setDocName( filename ); + statusBar()->message( tr("Printing...") ); + PrintOut pout( &printer ); + ContextLVI *c = (ContextLVI *) lv->firstChild(); + while ( c != 0 ) { + setCurrentContextItem( c ); + pout.vskip(); + pout.setRule( PrintOut::ThickRule ); + pout.setGuide( c->context() ); + pout.addBox( 100, tr("Context: %1").arg(c->context()), + PrintOut::Strong ); + pout.flushLine(); + pout.addBox( 4 ); + pout.addBox( 92, c->comment(), PrintOut::Emphasis ); + pout.flushLine(); + pout.setRule( PrintOut::ThickRule ); + + MessageLVI *m = (MessageLVI *) slv->firstChild(); + while ( m != 0 ) { + pout.setRule( PrintOut::ThinRule ); + + TQString type; + switch ( m->message().type() ) { + case MetaTranslatorMessage::Finished: + type = tr( "finished" ); + break; + case MetaTranslatorMessage::Unfinished: + type = m->danger() ? tr( "unresolved" ) : TQString( "unfinished" ); + break; + case MetaTranslatorMessage::Obsolete: + type = tr( "obsolete" ); + break; + default: + type = TQString( "" ); + } + pout.addBox( 40, m->sourceText() ); + pout.addBox( 4 ); + pout.addBox( 40, m->translation() ); + pout.addBox( 4 ); + pout.addBox( 12, type, PrintOut::Normal, TQt::AlignRight ); + if ( !m->comment().isEmpty() ) { + pout.flushLine(); + pout.addBox( 4 ); + pout.addBox( 92, m->comment(), PrintOut::Emphasis ); + } + pout.flushLine( TRUE ); + + if ( pout.pageNum() != pageNum ) { + pageNum = pout.pageNum(); + statusBar()->message( tr("Printing... (page %1)") + .arg(pageNum) ); + } + m = (MessageLVI *) m->nextSibling(); + } + c = (ContextLVI *) c->nextSibling(); + } + pout.flushLine( TRUE ); + TQApplication::restoreOverrideCursor(); + statusBar()->message( tr("Printing completed"), MessageMS ); + } else { + statusBar()->message( tr("Printing aborted"), MessageMS ); + } +} + +void TrWindow::find() +{ + h->hide(); + f->show(); + f->setActiveWindow(); + f->raise(); +} + +void TrWindow::findAgain() +{ + int pass = 0; + int oldItemNo = itemToIndex( slv, slv->currentItem() ); + TQString delayedMsg; + TQListViewItem * j = foundScope; + TQListViewItem * k = indexToItem( slv, foundItem ); + TQListViewItem * oldScope = lv->currentItem(); + + if ( lv->childCount() == 0 ) + return; +#if 1 + /* + As long as we don't implement highlighting of the text in the TQTextView, + we may have only one match per message. + */ + foundOffset = (int) 0x7fffffff; +#else + foundOffset++; +#endif + slv->setUpdatesEnabled( FALSE ); + do { + // Iterate through every item in all contexts + if ( j == 0 ) { + j = lv->firstChild(); + setCurrentContextItem( j ); + if ( foundScope != 0 ) + delayedMsg = tr("Search wrapped."); + } + if ( k == 0 ) + k = slv->firstChild(); + + while ( k ) { + MessageLVI * m = (MessageLVI *) k; + switch ( foundWhere ) { + case 0: + foundWhere = FindDialog::SourceText; + foundOffset = 0; + // fall-through + case FindDialog::SourceText: + if ( searchItem( m->sourceText(), j, k ) ) { + f->hide(); + if ( !delayedMsg.isEmpty() ) + statusBar()->message( delayedMsg, MessageMS ); + return; + } + foundWhere = FindDialog::Translations; + foundOffset = 0; + // fall-through + case FindDialog::Translations: + if ( searchItem( m->translation(), j, k ) ) { + f->hide(); + if ( !delayedMsg.isEmpty() ) + statusBar()->message( delayedMsg, MessageMS ); + return; + } + foundWhere = FindDialog::Comments; + foundOffset = 0; + // fall-through + case FindDialog::Comments: + if ( searchItem( ((ContextLVI *) j)->fullContext(), j, k) ) { + f->hide(); + if ( !delayedMsg.isEmpty() ) + statusBar()->message( delayedMsg, MessageMS ); + return; + } + foundWhere = 0; + foundOffset = 0; + } + k = k->nextSibling(); + } + + j = j->nextSibling(); + if ( j ) { + setCurrentContextItem( j ); + k = slv->firstChild(); + } + } while ( pass++ != lv->childCount() ); + + // This is just to keep the current scope and source text item + // selected after a search failed. + if ( oldScope ) { + setCurrentContextItem( oldScope ); + TQListViewItem * tmp = indexToItem( slv, oldItemNo ); + if( tmp ) + setCurrentMessageItem( tmp ); + } else { + if( lv->firstChild() ) + setCurrentContextItem( lv->firstChild() ); + if( slv->firstChild() ) + setCurrentMessageItem( slv->firstChild() ); + } + + slv->setUpdatesEnabled( TRUE ); + slv->triggerUpdate(); + qApp->beep(); + TQMessageBox::warning( this, tr("TQt Linguist"), + TQString( tr("Cannot find the string '%1'.") ).arg(findText) ); + foundItem = 0; + foundWhere = 0; + foundOffset = 0; +} + +void TrWindow::replace() +{ + f->hide(); + h->show(); + h->setActiveWindow(); + h->raise(); +} + +int TrWindow::itemToIndex( TQListView * view, TQListViewItem * item ) +{ + int no = 0; + TQListViewItem * tmp; + + if( view && item ){ + if( (tmp = view->firstChild()) != 0 ) + do { + no++; + tmp = tmp->nextSibling(); + } while( tmp && (tmp != item) ); + } + return no; +} + +TQListViewItem * TrWindow::indexToItem( TQListView * view, int index ) +{ + TQListViewItem * item = 0; + + if ( view && index > 0 ) { + item = view->firstChild(); + while( item && index-- > 0 ) + item = item->nextSibling(); + } + return item; +} + +bool TrWindow::searchItem( const TQString & searchWhat, TQListViewItem * j, + TQListViewItem * k ) +{ + if ( (findWhere & foundWhere) != 0 ) { + foundOffset = searchWhat.find( findText, foundOffset, findMatchCase ); + if ( foundOffset >= 0 ) { + foundItem = itemToIndex( slv, k ); + foundScope = j; + setCurrentMessageItem( k ); + slv->setUpdatesEnabled( TRUE ); + slv->triggerUpdate(); + return TRUE; + } + } + foundOffset = 0; + return FALSE; +} + +void TrWindow::newPhraseBook() +{ + TQString name; + for (;;) { + name = TQFileDialog::getSaveFileName( TQString::null, + tr("TQt phrase books (*.qph)\n" + "All files (*)"), + this, "new_phrasebook", + tr("Create New Phrase Book") ); + if ( !TQFile::exists(name) ) + break; + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("A file called '%1' already exists." + " Please choose another name.").arg(name) ); + } + if ( !name.isEmpty() ) { + PhraseBook pb; + if ( savePhraseBook(name, pb) ) { + if ( openPhraseBook(name) ) + statusBar()->message( tr("Phrase book created."), MessageMS ); + } + } +} + +void TrWindow::openPhraseBook() +{ + TQString phrasebooks( qInstallPathData() ); + TQString name = TQFileDialog::getOpenFileName( phrasebooks + "/phrasebooks", + tr("TQt phrase books (*.qph)\n" + "All files (*)"), + this, "open_phrasebook", + tr("Open Phrase Book") ); + if ( !name.isEmpty() && !phraseBookNames.contains(name) ) { + if ( openPhraseBook(name) ) { + int n = (int)(phraseBooks.at( phraseBooks.count() - 1 )->count()); + statusBar()->message( tr("%1 phrase(s) loaded.").arg(n), + MessageMS ); + } + } +} + +void TrWindow::closePhraseBook( int id ) +{ + int index = closePhraseBookp->indexOf( id ); + phraseBooks.remove( index ); + phraseBookNames.remove( phraseBookNames.at(index) ); + updatePhraseDict(); + + dirtyItem = index; // remove the item next time the menu is opened + editPhraseBookp->removeItem( editPhraseBookp->idAt(index) ); + printPhraseBookp->removeItem( printPhraseBookp->idAt(index) ); +} + +void TrWindow::editPhraseBook( int id ) +{ + int index = editPhraseBookp->indexOf( id ); + PhraseBookBox box( phraseBookNames[index], *phraseBooks.at(index), this, + "phrase book box", TRUE ); + box.setCaption( tr("%1 - %2").arg(tr("TQt Linguist")) + .arg(friendlyPhraseBookName(index)) ); + box.resize( 500, 300 ); + box.exec(); + *phraseBooks.at( index ) = box.phraseBook(); + updatePhraseDict(); +} + +void TrWindow::printPhraseBook( int id ) +{ + int index = printPhraseBookp->indexOf( id ); + int pageNum = 0; + + if ( printer.setup(this) ) { + printer.setDocName( phraseBookNames[index] ); + statusBar()->message( tr("Printing...") ); + PrintOut pout( &printer ); + PhraseBook *phraseBook = phraseBooks.at( index ); + PhraseBook::Iterator p; + pout.setRule( PrintOut::ThinRule ); + for ( p = phraseBook->begin(); p != phraseBook->end(); ++p ) { + pout.setGuide( (*p).source() ); + pout.addBox( 29, (*p).source() ); + pout.addBox( 4 ); + pout.addBox( 29, (*p).target() ); + pout.addBox( 4 ); + pout.addBox( 34, (*p).definition(), PrintOut::Emphasis ); + + if ( pout.pageNum() != pageNum ) { + pageNum = pout.pageNum(); + statusBar()->message( tr("Printing... (page %1)") + .arg(pageNum) ); + } + pout.setRule( PrintOut::NoRule ); + pout.flushLine( TRUE ); + } + pout.flushLine( TRUE ); + statusBar()->message( tr("Printing completed"), MessageMS ); + } else { + statusBar()->message( tr("Printing aborted"), MessageMS ); + } +} + +void TrWindow::revertSorting() +{ + lv->setSorting( 0 ); + slv->setSorting( 0 ); +} + +void TrWindow::manual() +{ + TQAssistantClient *ac = new TQAssistantClient( qInstallPathBins(), this ); + ac->showPage( TQString( qInstallPathDocs() ) + "/html/linguist-manual.html" ); +} + +void TrWindow::about() +{ + AboutDialog about( this, 0, TRUE ); + about.versionLabel->setText( tr("Version %1").arg(QT_VERSION_STR) ); + about.exec(); +} + +void TrWindow::aboutTQt() +{ + TQMessageBox::aboutTQt( this, tr("TQt Linguist") ); +} + +void TrWindow::setupPhrase() +{ + bool enabled = !phraseBooks.isEmpty(); + phrasep->setItemEnabled( closePhraseBookId, enabled ); + phrasep->setItemEnabled( editPhraseBookId, enabled ); + phrasep->setItemEnabled( printPhraseBookId, enabled ); +} + +void TrWindow::closeEvent( TQCloseEvent *e ) +{ + if ( maybeSave() ) + e->accept(); + else + e->ignore(); +} + +bool TrWindow::maybeSave() +{ + if ( dirty ) { + switch ( TQMessageBox::information(this, tr("TQt Linguist"), + tr("Do you want to save '%1'?") + .arg(filename), + TQMessageBox::Yes | TQMessageBox::Default, + TQMessageBox::No, + TQMessageBox::Cancel | TQMessageBox::Escape ) ) + { + case TQMessageBox::Cancel: + return FALSE; + case TQMessageBox::Yes: + save(); + return !dirty; + case TQMessageBox::No: + break; + } + } + return TRUE; +} + +void TrWindow::updateCaption() +{ + TQString cap; + bool enable = !filename.isEmpty(); + saveAct->setEnabled( enable ); + saveAsAct->setEnabled( enable ); + releaseAct->setEnabled( enable ); + printAct->setEnabled( enable ); + acceleratorsAct->setEnabled( enable ); + endingPunctuationAct->setEnabled( enable ); + phraseMatchesAct->setEnabled( enable ); + revertSortingAct->setEnabled( enable ); + + if ( filename.isEmpty() ) + cap = tr( "TQt Linguist by Trolltech" ); + else + cap = tr( "%1 - %2" ).arg( tr("TQt Linguist by Trolltech") ) + .arg( filename ); + setCaption( cap ); + modified->setEnabled( dirty ); +} + +// +// New scope selected - build a new list of source text items +// for that scope. +// +void TrWindow::showNewScope( TQListViewItem *item ) +{ + static ContextLVI * oldContext = 0; + + if( item != 0 ) { + ContextLVI * c = (ContextLVI *) item; + bool upe = slv->isUpdatesEnabled(); + slv->setUpdatesEnabled( FALSE ); + slv->viewport()->setUpdatesEnabled( FALSE ); + if ( oldContext != 0 ) { + MessageLVI * tmp; + slv->blockSignals( TRUE ); + while ( (tmp = (MessageLVI *) slv->firstChild()) != 0 ) + oldContext->appendMessageItem( slv, tmp ); + slv->blockSignals( FALSE ); + } + MessageLVI * tmp; + while ( c->messageItemsInList() ) { + tmp = c->takeMessageItem( c->messageItemsInList() - 1); + slv->insertItem( tmp ); + tmp->updateTranslationText(); + } + + // Make sure that we update the source text and translation text. Use the first message in the new scope. + setCurrentMessageItem(slv->firstChild()); + // This must be explicitly called since the signal is not emitted if the context only contains one item + showNewCurrent(slv->firstChild()); + slv->viewport()->setUpdatesEnabled( upe ); + slv->setUpdatesEnabled( upe ); + if( upe ) + slv->triggerUpdate(); + oldContext = (ContextLVI *) item; + statusBar()->clear(); + } +} + +void TrWindow::showNewCurrent( TQListViewItem *item ) +{ + messageIsShown = (item != 0); + MessageLVI *m = (MessageLVI *) item; + ContextLVI *c = (ContextLVI *) m ? m->contextLVI() : 0; + + if ( messageIsShown ) { + me->showMessage( m->sourceText(), m->comment(), c->fullContext(), + m->translation(), m->message().type(), + getPhrases(m->sourceText()) ); + if ( (m->message().type() != MetaTranslatorMessage::Finished) && + m->danger() ) + danger( m->sourceText(), m->translation(), TRUE ); + else + statusBar()->clear(); + + doneAndNextAct->setEnabled( m->message().type() != + MetaTranslatorMessage::Obsolete ); + } else { + if ( item == 0 ) + me->showNothing(); + else + me->showContext( c->fullContext(), c->finished() ); + doneAndNextAct->setEnabled( FALSE ); + } + doneAndNextAlt->setEnabled( doneAndNextAct->isEnabled() ); + + selectAllAct->setEnabled( messageIsShown ); +} + +void TrWindow::updateTranslation( const TQString& translation ) +{ + TQListViewItem *item = slv->currentItem(); + if ( item != 0 ) { + MessageLVI *m = (MessageLVI *) item; + if ( translation != m->translation() ) { + bool dngr; + m->setTranslation( translation ); + if ( m->finished() && + (dngr = danger( m->sourceText(), m->translation(), TRUE )) ) { + numFinished -= 1; + m->setDanger( dngr ); + m->setFinished( FALSE ); + m->contextLVI()->updateStatus(); + updateProgress(); + } + tor.insert( m->message() ); + if ( !dirty ) { + dirty = TRUE; + updateCaption(); + } + m->updateTranslationText(); + } + } +} + +void TrWindow::updateFinished( bool finished ) +{ + TQListViewItem *item = slv->currentItem(); + if ( item != 0 ) { + MessageLVI *m = (MessageLVI *) item; + if ( finished != m->finished() ) { + numFinished += finished ? +1 : -1; + updateProgress(); + m->setFinished( finished ); + bool oldDanger = m->danger(); + m->setDanger( /*m->finished() &&*/ + danger(m->sourceText(), m->translation(), + !oldDanger) ); + if ( !oldDanger && m->danger() ) + qApp->beep(); + tor.insert( m->message() ); + if ( !dirty ) { + dirty = TRUE; + updateCaption(); + } + } + } +} + +void TrWindow::doneAndNext() +{ + MessageLVI * m = (MessageLVI *) slv->currentItem(); + bool dngr = FALSE; + + if ( !m ) return; + dngr = danger( m->sourceText(), m->translation(), TRUE ); + if ( !dngr ) { + me->finishAndNext(); + m->contextLVI()->updateStatus(); + } else { + if ( m->danger() != dngr ) + m->setDanger( dngr ); + tor.insert( m->message() ); + if ( !dirty ) { + dirty = TRUE; + updateCaption(); + } + qApp->beep(); + } + updateStatistics(); +} + +void TrWindow::toggleFinished( TQListViewItem *item, const TQPoint& /* p */, + int column ) +{ + if ( item != 0 && column == 0 ) { + MessageLVI *m = (MessageLVI *) item; + bool dngr = FALSE; + + if ( m->message().type() == MetaTranslatorMessage::Unfinished ) { + dngr = danger( m->sourceText(), m->translation(), TRUE ); + } + if ( !dngr && m->message().type() != MetaTranslatorMessage::Obsolete) { + setCurrentMessageItem( m ); + me->setFinished( !m->finished() ); + m->contextLVI()->updateStatus(); + } else { + bool oldDanger = m->danger(); + m->setDanger( danger(m->sourceText(), m->translation(), + !oldDanger) ); + if ( !oldDanger && m->danger() ) + qApp->beep(); + tor.insert( m->message() ); + if ( !dirty ) { + dirty = TRUE; + updateCaption(); + } + } + updateStatistics(); + } +} + +void TrWindow::nextUnfinished() +{ + if ( nextUnfinishedAct->isEnabled() ) { + // Select a message to translate, grab the first available if + // there are no current selection. + TQListViewItem * cItem = lv->currentItem(); // context item + TQListViewItem * mItem = slv->currentItem(); // message item + + // Make sure an item is selected from both the context and the + // message list. + if( (mItem == 0) && !(mItem = slv->firstChild()) ) { + if( (cItem == 0) && !(cItem = lv->firstChild()) ) { + statusBar()->message( tr("No phrase to translate."), + MessageMS ); + qApp->beep(); + return; + } else { + showNewScope( cItem ); + while( cItem && !(mItem = slv->firstChild()) ) { + // no children in this node - try next one + cItem = cItem->nextSibling(); + showNewScope( cItem ); + } + setCurrentContextItem( cItem ); + if( mItem ) { + setCurrentMessageItem( mItem ); + } else { + statusBar()->message( tr("No phrase to translate."), + MessageMS ); + qApp->beep(); + return; + } + } + } else { + setCurrentMessageItem( mItem ); + } + + MessageLVI * m = (MessageLVI *) mItem; + MessageLVI * n; + ContextLVI * p = (ContextLVI *) cItem; + ContextLVI * q; + + // Find the next Unfinished sibling within the same context. + m = (MessageLVI *) mItem->nextSibling(); + n = m; + do { + if ( n == 0 ) + break; + if ( n && !n->finished() && n != mItem ) { + setCurrentMessageItem( n ); + return; + } + n = (MessageLVI *) n->nextSibling(); + } while ( n != m ); + + // If all siblings are Finished or Obsolete, look in the first + // Unfinished context. + p = (ContextLVI *) p->nextSibling(); + q = p; + do { + if ( q == 0 ) + q = (ContextLVI *) lv->firstChild(); + if ( q && !q->finished() ) { + showNewScope( q ); + setCurrentContextItem( q ); + n = (MessageLVI *) slv->firstChild(); + while ( n && n->finished() ) + n = (MessageLVI *) n->nextSibling(); + if ( n && q ) { + setCurrentMessageItem( n ); + showNewCurrent( n ); + return; + } + } + q = (ContextLVI *) q->nextSibling(); + } while ( q != p ); + } + + // If no Unfinished message is left, the user has finished the job. We + // congratulate on a job well done with this ringing bell. + statusBar()->message( tr("No untranslated phrases left."), MessageMS ); + qApp->beep(); +} + +static TQListViewItem * lastChild( TQListView * view ) +{ + if ( view ) { + TQListViewItem * ret, * tmp; + ret = view->firstChild(); + while ( ret ) { + tmp = ret->nextSibling(); + if ( tmp == 0 ) + return ret; + ret = tmp; + } + } + return 0; +} + +void TrWindow::prevUnfinished() +{ + if ( prevUnfinishedAct->isEnabled() ) { + // Select a message to translate, grab the first available if + // there are no current selection. + TQListViewItem * cItem = lv->currentItem(); // context item + TQListViewItem * mItem = slv->currentItem(); // message item + + // Make sure an item is selected from both the context and the + // message list. + if( (mItem == 0) && !(mItem = slv->firstChild()) ) { + if( (cItem == 0) && !(cItem = lv->firstChild()) ) { + statusBar()->message( tr("No phrase to translate."), + MessageMS ); + qApp->beep(); + return; + } else { + showNewScope( cItem ); + while( cItem && !(mItem = slv->firstChild()) ) { + // no children in this node - try next one + cItem = cItem->nextSibling(); + showNewScope( cItem ); + } + setCurrentContextItem( cItem ); + if( mItem ) { + setCurrentMessageItem( cItem ); + } else { + statusBar()->message( tr("No phrase to translate."), + MessageMS ); + qApp->beep(); + return; + } + } + } else { + setCurrentMessageItem( mItem ); + } + + MessageLVI * m = (MessageLVI *) mItem; + MessageLVI * n; + ContextLVI * p = (ContextLVI *) cItem; + ContextLVI * q; + + // Find the next Unfinished sibling within the same context. + n = m; + do { + n = (MessageLVI * ) n->itemAbove(); + if ( n == 0 ) + break; + if ( n && !n->finished() ) { + setCurrentMessageItem( n ); + return; + } + } while ( !((ContextLVI *) cItem)->finished() && n != 0 ); + + // If all siblings are Finished or Obsolete, look in the prev + // Unfinished context. + q = p; + do { + q = (ContextLVI *) q->itemAbove(); + if ( q == 0 ) + q = (ContextLVI *) lastChild( lv ); + if ( q && !q->finished() ) { + showNewScope( q ); + setCurrentContextItem( q ); + n = (MessageLVI *) lastChild( slv ); + while ( n && n->finished() ) + n = (MessageLVI *) n->itemAbove(); + if ( n && q ) { + setCurrentMessageItem( n ); + return; + } + } + } while ( q != 0 ); + } + statusBar()->message( tr("No untranslated phrases left."), MessageMS ); + qApp->beep(); +} + +void TrWindow::prev() +{ + TQListViewItem * cItem = lv->currentItem(); // context item + TQListViewItem * mItem = slv->currentItem(); // message item + TQListViewItem * tmp; + + if ( !cItem ) { + cItem = lv->firstChild(); + if ( !cItem ) return; + setCurrentContextItem( cItem ); + } + + if ( !mItem ) { + mItem = lastChild( slv ); + if ( !mItem ) return; + setCurrentMessageItem( mItem ); + } else { + if ( (tmp = mItem->itemAbove()) != 0 ) { + setCurrentMessageItem( tmp ); + return; + } else { + if ( (tmp = cItem->itemAbove()) == 0 ) { + tmp = lastChild( lv ); + } + if ( !tmp ) return; + setCurrentContextItem( tmp ); + setCurrentMessageItem( lastChild( slv ) ); + } + } +} + +void TrWindow::next() +{ + TQListViewItem * cItem = lv->currentItem(); // context item + TQListViewItem * mItem = slv->currentItem(); // message item + TQListViewItem * tmp; + + if ( !cItem ) { + cItem = lv->firstChild(); + if ( !cItem ) return; + setCurrentContextItem( cItem ); + } + + if ( !mItem ) { + mItem = slv->firstChild(); + if ( !mItem ) return; + setCurrentMessageItem( mItem ); + } else { + if ( (tmp = mItem->nextSibling()) != 0 ) { + setCurrentMessageItem( tmp ); + return; + } else { + if ( (tmp = cItem->nextSibling()) == 0 ) { + tmp = lv->firstChild(); + } + if ( !tmp ) return; + setCurrentContextItem( tmp ); + setCurrentMessageItem( slv->firstChild() ); + } + } +} + + +void TrWindow::findNext( const TQString& text, int where, bool matchCase ) +{ + findText = text; + if ( findText.isEmpty() ) + findText = TQString( "magicwordthatyoushouldavoid" ); + findWhere = where; + findMatchCase = matchCase; + findAgainAct->setEnabled( TRUE ); + findAgain(); +} + +void TrWindow::revalidate() +{ + ContextLVI *c = (ContextLVI *) lv->firstChild(); + TQListViewItem * oldScope = lv->currentItem(); + int oldItemNo = itemToIndex( slv, slv->currentItem() ); + slv->setUpdatesEnabled( FALSE ); + + while ( c != 0 ) { + showNewScope( c ); + MessageLVI *m = (MessageLVI *) slv->firstChild(); + while ( m != 0 ) { + m->setDanger( danger(m->sourceText(), m->translation()) && + m->message().type() == MetaTranslatorMessage::Finished ); + m = (MessageLVI *) m->nextSibling(); + } + c = (ContextLVI *) c->nextSibling(); + } + + if ( oldScope ){ + showNewScope( oldScope ); + TQListViewItem * tmp = indexToItem( slv, oldItemNo ); + if( tmp ) + setCurrentMessageItem( tmp ); + } + slv->setUpdatesEnabled( TRUE ); + slv->triggerUpdate(); +} + +TQString TrWindow::friendlyString( const TQString& str ) +{ + TQString f = str.lower(); + f.replace( TQRegExp(TQString("[.,:;!?()-]")), TQString(" ") ); + f.replace( "&", TQString("") ); + f = f.simplifyWhiteSpace(); + f = f.lower(); + return f; +} + +void TrWindow::setupMenuBar() +{ + TQMenuBar * m = menuBar(); + TQPopupMenu * filep = new TQPopupMenu( this ); + TQPopupMenu * editp = new TQPopupMenu( this ); + TQPopupMenu * translationp = new TQPopupMenu( this ); + TQPopupMenu * validationp = new TQPopupMenu( this ); + validationp->setCheckable( TRUE ); + phrasep = new TQPopupMenu( this ); + closePhraseBookp = new TQPopupMenu( this ); + editPhraseBookp = new TQPopupMenu( this ); + printPhraseBookp = new TQPopupMenu( this ); + TQPopupMenu * viewp = new TQPopupMenu( this ); + viewp->setCheckable( TRUE ); + TQPopupMenu * helpp = new TQPopupMenu( this ); + + m->insertItem( tr("&File"), filep ); + m->insertItem( tr("&Edit"), editp ); + m->insertItem( tr("&Translation"), translationp ); + m->insertItem( tr("V&alidation"), validationp ); + m->insertItem( tr("&Phrases"), phrasep ); + m->insertItem( tr("&View"), viewp ); + m->insertSeparator(); + m->insertItem( tr("&Help"), helpp ); + + connect( closePhraseBookp, SIGNAL(activated(int)), + this, SLOT(closePhraseBook(int)) ); + connect( closePhraseBookp, SIGNAL(aboutToShow()), + this, SLOT(updateClosePhraseBook()) ); + connect( editPhraseBookp, SIGNAL(activated(int)), + this, SLOT(editPhraseBook(int)) ); + connect( printPhraseBookp, SIGNAL(activated(int)), + this, SLOT(printPhraseBook(int)) ); + // File menu + openAct = new Action( filep, tr("&Open..."), this, SLOT(open()), + "fileopen.png", TQAccel::stringToKey(tr("Ctrl+O")) ); + + filep->insertSeparator(); + + saveAct = new Action( filep, tr("&Save"), this, SLOT(save()), + "filesave.png", TQAccel::stringToKey(tr("Ctrl+S")) ); + saveAsAct = new Action( filep, tr("Save &As..."), this, SLOT(saveAs()) ); + releaseAct = new Action( filep, tr("&Release..."), this, SLOT(release()) ); + filep->insertSeparator(); + printAct = new Action( filep, tr("&Print..."), this, SLOT(print()), + "print.png", TQAccel::stringToKey(tr("Ctrl+P")) ); + + filep->insertSeparator(); + + recentFilesMenu = new TQPopupMenu( this ); + filep->insertItem( tr("Re¢ly opened files"), recentFilesMenu ); + connect( recentFilesMenu, SIGNAL(aboutToShow()), this, + SLOT(setupRecentFilesMenu()) ); + connect( recentFilesMenu, SIGNAL(activated( int )), this, + SLOT(recentFileActivated( int )) ); + + filep->insertSeparator(); + + exitAct = new Action( filep, tr("E&xit"), this, SLOT(close()), + TQString::null, TQAccel::stringToKey(tr("Ctrl+Q")) ); + // Edit menu + undoAct = new Action( editp, tr("&Undo"), me, SLOT(undo()), + "undo.png", TQAccel::stringToKey(tr("Ctrl+Z")) ); + undoAct->setEnabled( FALSE ); + connect( me, SIGNAL(undoAvailable(bool)), undoAct, SLOT(setEnabled(bool)) ); + redoAct = new Action( editp, tr("&Redo"), me, SLOT(redo()), + "redo.png", TQAccel::stringToKey(tr("Ctrl+Y")) ); + redoAct->setEnabled( FALSE ); + connect( me, SIGNAL(redoAvailable(bool)), redoAct, SLOT(setEnabled(bool)) ); + editp->insertSeparator(); + cutAct = new Action( editp, tr("Cu&t"), me, SLOT(cut()), + "editcut.png", TQAccel::stringToKey(tr("Ctrl+X")) ); + cutAct->setEnabled( FALSE ); + connect( me, SIGNAL(cutAvailable(bool)), cutAct, SLOT(setEnabled(bool)) ); + copyAct = new Action( editp, tr("&Copy"), me, SLOT(copy()), + "editcopy.png", TQAccel::stringToKey(tr("Ctrl+C")) ); + copyAct->setEnabled( FALSE ); + connect( me, SIGNAL(copyAvailable(bool)), copyAct, SLOT(setEnabled(bool)) ); + pasteAct = new Action( editp, tr("&Paste"), me, SLOT(paste()), + "editpaste.png", TQAccel::stringToKey(tr("Ctrl+V")) ); + pasteAct->setEnabled( FALSE ); + connect( me, SIGNAL(pasteAvailable(bool)), + pasteAct, SLOT(setEnabled(bool)) ); + selectAllAct = new Action( editp, tr("Select &All"), me, SLOT(selectAll()), + TQString::null, TQAccel::stringToKey(tr("Ctrl+A")) ); + selectAllAct->setEnabled( FALSE ); + editp->insertSeparator(); + findAct = new Action( editp, tr("&Find..."), this, SLOT(find()), + "searchfind.png", TQAccel::stringToKey(tr("Ctrl+F")) ); + findAct->setEnabled( FALSE ); + findAgainAct = new Action( editp, tr("Find &Next"), + this, SLOT(findAgain()), TQString::null, Key_F3 ); + findAgainAct->setEnabled( FALSE ); +#ifdef notyet + replaceAct = new Action( editp, tr("&Replace..."), this, SLOT(replace()), + TQAccel::stringToKey(tr("Ctrl+H")) ); + replaceAct->setEnabled( FALSE ); +#endif + + // Translation menu + // when updating the accelerators, remember the status bar + prevUnfinishedAct = new Action( translationp, tr("&Prev Unfinished"), + this, SLOT(prevUnfinished()), + "prevunfinished.png", TQAccel::stringToKey(tr("Ctrl+K")) ); + nextUnfinishedAct = new Action( translationp, tr("&Next Unfinished"), + this, SLOT(nextUnfinished()), + "nextunfinished.png", TQAccel::stringToKey(tr("Ctrl+L")) ); + + prevAct = new Action( translationp, tr("P&rev"), + this, SLOT(prev()), "prev.png", + TQAccel::stringToKey(tr("Ctrl+Shift+K")) ); + nextAct = new Action( translationp, tr("Ne&xt"), + this, SLOT(next()), "next.png", + TQAccel::stringToKey(tr("Ctrl+Shift+L")) ); + doneAndNextAct = new Action( translationp, tr("Done and &Next"), + this, SLOT(doneAndNext()), "doneandnext.png", + TQAccel::stringToKey(tr("Ctrl+Enter")) ); + doneAndNextAlt = new TQAction( this ); + doneAndNextAlt->setAccel( TQAccel::stringToKey(tr("Ctrl+Return")) ); + connect( doneAndNextAlt, SIGNAL(activated()), this, SLOT(doneAndNext()) ); + beginFromSourceAct = new Action( translationp, tr("&Begin from Source"), + me, SLOT(beginFromSource()), + TQString::null, TQAccel::stringToKey(tr("Ctrl+B")) ); + connect( me, SIGNAL(updateActions(bool)), beginFromSourceAct, + SLOT(setEnabled(bool)) ); + + // Phrasebook menu + newPhraseBookAct = new Action( phrasep, tr("&New Phrase Book..."), + this, SLOT(newPhraseBook()), + TQString::null, TQAccel::stringToKey(tr("Ctrl+N")) ); + openPhraseBookAct = new Action( phrasep, tr("&Open Phrase Book..."), + this, SLOT(openPhraseBook()), + "book.png", TQAccel::stringToKey(tr("Ctrl+H")) ); + closePhraseBookId = phrasep->insertItem( tr("&Close Phrase Book"), + closePhraseBookp ); + phrasep->insertSeparator(); + editPhraseBookId = phrasep->insertItem( tr("&Edit Phrase Book..."), + editPhraseBookp ); + printPhraseBookId = phrasep->insertItem( tr("&Print Phrase Book..."), + printPhraseBookp ); + connect( phrasep, SIGNAL(aboutToShow()), this, SLOT(setupPhrase()) ); + + // Validation menu + acceleratorsAct = new Action( validationp, tr("&Accelerators"), + this, SLOT(revalidate()), "accelerator.png", 0, TRUE ); + acceleratorsAct->setOn( TRUE ); + endingPunctuationAct = new Action( validationp, tr("&Ending Punctuation"), + this, SLOT(revalidate()), "punctuation.png", 0, TRUE ); + endingPunctuationAct->setOn( TRUE ); + phraseMatchesAct = new Action( validationp, tr("&Phrase Matches"), + this, SLOT(revalidate()), "phrase.png", 0, TRUE ); + phraseMatchesAct->setOn( TRUE ); + + // View menu + revertSortingAct = new Action( viewp, tr("&Revert Sorting"), + this, SLOT(revertSorting()) ); + doGuessesAct = new Action( viewp, tr("&Display guesses"), + this, SLOT(toggleGuessing()) ); + doGuessesAct->setToggleAction( TRUE ); + doGuessesAct->setOn( TRUE ); + toggleStats = new Action( viewp, tr("&Statistics"), this, SLOT(toggleStatistics()) ); + toggleStats->setToggleAction( TRUE ); + viewp->insertSeparator(); + viewp->insertItem( tr("Vie&ws"), createDockWindowMenu( NoToolBars ) ); + viewp->insertItem( tr("&Toolbars"), createDockWindowMenu( OnlyToolBars ) ); + + // Help + manualAct = new Action( helpp, tr("&Manual"), this, SLOT(manual()), 0, + Key_F1 ); + helpp->insertSeparator(); + aboutAct = new Action( helpp, tr("&About"), this, SLOT(about()) ); + aboutTQtAct = new Action( helpp, tr("About &TQt"), this, SLOT(aboutTQt()) ); + helpp->insertSeparator(); + whatsThisAct = new Action( helpp, tr("&What's This?"), + this, SLOT(whatsThis()), "whatsthis.xpm", SHIFT + Key_F1 ); + + openAct->setWhatsThis( tr("Open a TQt translation source file (TS file) for" + " editing.") ); + saveAct->setWhatsThis( tr("Save changes made to this TQt translation " + "source file.") ); + saveAsAct->setWhatsThis( tr("Save changes made to this TQt translation" + "source file into a new file.") ); + releaseAct->setWhatsThis( tr("Create a TQt message file suitable for" + " released applications" + " from the current message file.") ); + printAct->setWhatsThis( tr("Print a list of all the phrases in the current" + " TQt translation source file.") ); + exitAct->setWhatsThis( tr("Close this window and exit.") ); + + undoAct->setWhatsThis( tr("Undo the last editing operation performed on the" + " translation.") ); + redoAct->setWhatsThis( tr("Redo an undone editing operation performed on" + " the translation.") ); + cutAct->setWhatsThis( tr("Copy the selected translation text to the" + " clipboard and deletes it.") ); + copyAct->setWhatsThis( tr("Copy the selected translation text to the" + " clipboard.") ); + pasteAct->setWhatsThis( tr("Paste the clipboard text into the" + " translation.") ); + selectAllAct->setWhatsThis( tr("Select the whole translation text.") ); + findAct->setWhatsThis( tr("Search for some text in the translation " + "source file.") ); + findAgainAct->setWhatsThis( tr("Continue the search where it was left.") ); +#ifdef notyet + replaceAct->setWhatsThis( tr("Search for some text in the translation" + " source file and replace it by another" + " text.") ); +#endif + + newPhraseBookAct->setWhatsThis( tr("Create a new phrase book.") ); + openPhraseBookAct->setWhatsThis( tr("Open a phrase book to assist" + " translation.") ); + acceleratorsAct->setWhatsThis( tr("Toggle validity checks of" + " accelerators.") ); + endingPunctuationAct->setWhatsThis( tr("Toggle validity checks" + " of ending punctuation.") ); + phraseMatchesAct->setWhatsThis( tr("Toggle checking that phrase" + " suggestions are used.") ); + + revertSortingAct->setWhatsThis( tr("Sort the items back in the same order" + " as in the message file.") ); + + doGuessesAct->setWhatsThis( tr("Set whether or not to display translation guesses.") ); + manualAct->setWhatsThis( tr("Display the manual for %1.") + .arg(tr("TQt Linguist")) ); + aboutAct->setWhatsThis( tr("Display information about %1.") + .arg(tr("TQt Linguist")) ); + aboutTQtAct->setWhatsThis( tr("Display information about the TQt toolkit by" + " Trolltech.") ); + whatsThisAct->setWhatsThis( tr("Enter What's This? mode.") ); + + beginFromSourceAct->setWhatsThis( tr("Copies the source text into" + " the translation field.") ); + nextAct->setWhatsThis( tr("Moves to the next item.") ); + prevAct->setWhatsThis( tr("Moves to the previous item.") ); + nextUnfinishedAct->setWhatsThis( tr("Moves to the next unfinished item.") ); + prevUnfinishedAct->setWhatsThis( tr("Moves to the previous unfinished item.") ); + doneAndNextAct->setWhatsThis( tr("Marks this item as done and moves to the" + " next unfinished item.") ); + doneAndNextAlt->setWhatsThis( doneAndNextAct->whatsThis() ); +} + +void TrWindow::setupToolBars() +{ + TQToolBar *filet = new TQToolBar( tr("File"), this ); + TQToolBar *editt = new TQToolBar( tr("Edit"), this ); + TQToolBar *translationst = new TQToolBar( tr("Translation"), this ); + TQToolBar *validationt = new TQToolBar( tr("Validation"), this ); + TQToolBar *helpt = new TQToolBar( tr("Help"), this ); + + openAct->addToToolbar( filet, tr("Open") ); + saveAct->addToToolbar( filet, tr("Save") ); + printAct->addToToolbar( filet, tr("Print") ); + filet->addSeparator(); + openPhraseBookAct->addToToolbar( filet, tr("Open Phrase Book") ); + + undoAct->addToToolbar( editt, tr("Undo") ); + redoAct->addToToolbar( editt, tr("Redo") ); + editt->addSeparator(); + cutAct->addToToolbar( editt, tr("Cut") ); + copyAct->addToToolbar( editt, tr("Copy") ); + pasteAct->addToToolbar( editt, tr("Paste") ); + editt->addSeparator(); + findAct->addToToolbar( editt, tr("Find") ); +#ifdef notyet + replaceAct->addToToolbar( editt, tr("Replace") ); +#endif + + // beginFromSourceAct->addToToolbar( translationst, + // tr("Begin from Source"), "searchfind" ); + prevAct->addToToolbar( translationst, tr("Prev") ); + nextAct->addToToolbar( translationst, tr("Next") ); + prevUnfinishedAct->addToToolbar( translationst, tr("Prev Unfinished") ); + nextUnfinishedAct->addToToolbar( translationst, tr("Next Unfinished") ); + doneAndNextAct->addToToolbar( translationst, tr("Done and Next") ); + + acceleratorsAct->addToToolbar( validationt, tr("Accelerators") ); + endingPunctuationAct->addToToolbar( validationt, tr("Punctuation") ); + phraseMatchesAct->addToToolbar( validationt, tr("Phrases") ); + + whatsThisAct->addToToolbar( helpt, tr("What's This?") ); +} + +void TrWindow::setCurrentContextItem( TQListViewItem *item ) +{ + lv->ensureItemVisible( item ); + lv->setSelected( item, TRUE ); +} + +void TrWindow::setCurrentMessageItem( TQListViewItem *item ) +{ + slv->ensureItemVisible( item ); + slv->setSelected( item, TRUE ); +} + +TQString TrWindow::friendlyPhraseBookName( int k ) +{ + return TQFileInfo( phraseBookNames[k] ).fileName(); +} + +bool TrWindow::openPhraseBook( const TQString& name ) +{ + PhraseBook *pb = new PhraseBook; + if ( !pb->load(name) ) { + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("Cannot read from phrase book '%1'.") + .arg(name) ); + return FALSE; + } + + int index = (int) phraseBooks.count(); + phraseBooks.append( pb ); + phraseBookNames.append( name ); + int id = closePhraseBookp->insertItem( friendlyPhraseBookName(index) ); + closePhraseBookp->setWhatsThis( id, tr("Close this phrase book.") ); + id = editPhraseBookp->insertItem( friendlyPhraseBookName(index) ); + editPhraseBookp->setWhatsThis( id, tr("Allow you to add, modify, or delete" + " phrases of this phrase book.") ); + id = printPhraseBookp->insertItem( friendlyPhraseBookName(index) ); + printPhraseBookp->setWhatsThis( id, tr("Print the entries of the phrase" + " book.") ); + updatePhraseDict(); + return TRUE; +} + +bool TrWindow::savePhraseBook( TQString& name, const PhraseBook& pb ) +{ + if ( !name.contains( ".qph" ) && !name.contains(".") ) + name += ".qph"; + + if ( !pb.save(name) ) { + TQMessageBox::warning( this, tr("TQt Linguist"), + tr("Cannot create phrase book '%1'.") + .arg(name) ); + return FALSE; + } + return TRUE; +} + +void TrWindow::updateProgress() +{ + if ( numNonobsolete == 0 ) + progress->setText( TQString(" " " ") ); + else + progress->setText( TQString(" %1/%2 ").arg(numFinished) + .arg(numNonobsolete) ); + prevUnfinishedAct->setEnabled( numFinished != numNonobsolete ); + nextUnfinishedAct->setEnabled( numFinished != numNonobsolete ); + prevAct->setEnabled( lv->firstChild() != 0 ); + nextAct->setEnabled( lv->firstChild() != 0 ); +} + +void TrWindow::updatePhraseDict() +{ + TQPtrListIterator pb = phraseBooks; + PhraseBook::Iterator p; + PhraseBook *ent; + phraseDict.clear(); + while ( pb.current() != 0 ) { + for ( p = (*pb)->begin(); p != (*pb)->end(); ++p ) { + TQString f = friendlyString( (*p).source() ); + if ( f.length() > 0 ) { + f = TQStringList::split( TQChar(' '), f ).first(); + ent = phraseDict.find( f ); + if ( ent == 0 ) { + ent = new PhraseBook; + phraseDict.insert( f, ent ); + } + ent->append( *p ); + } + } + ++pb; + } + revalidate(); +} + +PhraseBook TrWindow::getPhrases( const TQString& source ) +{ + PhraseBook phrases; + TQString f = friendlyString( source ); + TQStringList lookupWords = TQStringList::split( TQChar(' '), f ); + TQStringList::Iterator w; + PhraseBook::Iterator p; + + for ( w = lookupWords.begin(); w != lookupWords.end(); ++w ) { + PhraseBook *ent = phraseDict.find( *w ); + if ( ent != 0 ) { + for ( p = ent->begin(); p != ent->end(); ++p ) { + if ( f.find(friendlyString((*p).source())) >= 0 ) + phrases.append( *p ); + } + } + } + return phrases; +} + +bool TrWindow::danger( const TQString& source, const TQString& translation, + bool verbose ) +{ + if ( acceleratorsAct->isOn() ) { + int sk = TQAccel::shortcutKey( source ); + int tk = TQAccel::shortcutKey( translation ); + if ( sk == 0 && tk != 0 ) { + if ( verbose ) + statusBar()->message( tr("Accelerator possibly superfluous in" + " translation."), ErrorMS ); + return TRUE; + } else if ( sk != 0 && tk == 0 ) { + if ( verbose ) + statusBar()->message( tr("Accelerator possibly missing in" + " translation."), ErrorMS ); + return TRUE; + } + } + if ( endingPunctuationAct->isOn() ) { + if ( ending(source) != ending(translation) ) { + if ( verbose ) + statusBar()->message( tr("Translation does not end with the" + " same punctuation as the source" + " text."), ErrorMS ); + return TRUE; + } + } + if ( phraseMatchesAct->isOn() ) { + TQString fsource = friendlyString( source ); + TQString ftranslation = friendlyString( translation ); + TQStringList lookupWords = TQStringList::split( TQChar(' '), fsource ); + TQStringList::Iterator w; + PhraseBook::Iterator p; + + for ( w = lookupWords.begin(); w != lookupWords.end(); ++w ) { + PhraseBook *ent = phraseDict.find( *w ); + if ( ent != 0 ) { + for ( p = ent->begin(); p != ent->end(); ++p ) { + if ( fsource.find(friendlyString((*p).source())) < 0 || + ftranslation.find(friendlyString((*p).target())) >= 0 ) + break; + } + if ( p == ent->end() ) { + if ( verbose ) + statusBar()->message( tr("A phrase book suggestion for" + " '%1' was ignored.") + .arg(*w), ErrorMS ); + return TRUE; + } + } + } + } + if ( verbose ) + statusBar()->clear(); + + return FALSE; +} + +void TrWindow::readConfig() +{ + TQString keybase( "/TQt Linguist/" + + TQString::number( (QT_VERSION >> 16) & 0xff ) + + "." + TQString::number( (QT_VERSION >> 8) & 0xff ) + "/" ); + TQSettings config; + + config.insertSearchPath( TQSettings::Windows, "/Trolltech" ); + + TQRect r( pos(), size() ); + recentFiles = config.readListEntry( keybase + "RecentlyOpenedFiles" ); + if ( !config.readBoolEntry( keybase + "Geometry/MainwindowMaximized", FALSE ) ) { + r.setX( config.readNumEntry( keybase + "Geometry/MainwindowX", r.x() ) ); + r.setY( config.readNumEntry( keybase + "Geometry/MainwindowY", r.y() ) ); + r.setWidth( config.readNumEntry( keybase + "Geometry/MainwindowWidth", r.width() ) ); + r.setHeight( config.readNumEntry( keybase + "Geometry/MainwindowHeight", r.height() ) ); + + TQRect desk = TQApplication::desktop()->geometry(); + TQRect inter = desk.intersect( r ); + resize( r.size() ); + if ( inter.width() * inter.height() > ( r.width() * r.height() / 20 ) ) { + move( r.topLeft() ); + } + } + + TQDockWindow * dw; + dw = (TQDockWindow *) lv->parent(); + int place; + place = config.readNumEntry( keybase + "Geometry/ContextwindowInDock" ); + r.setX( config.readNumEntry( keybase + "Geometry/ContextwindowX" ) ); + r.setY( config.readNumEntry( keybase + "Geometry/ContextwindowY" ) ); + r.setWidth( config.readNumEntry( keybase + + "Geometry/ContextwindowWidth" ) ); + r.setHeight( config.readNumEntry( keybase + + "Geometry/ContextwindowHeight" ) ); + if ( place == TQDockWindow::OutsideDock ) { + dw->undock(); + dw->show(); + } + dw->setGeometry( r ); + + dw = (TQDockWindow *) slv->parent(); + place = config.readNumEntry( keybase + "Geometry/SourcewindowInDock" ); + r.setX( config.readNumEntry( keybase + "Geometry/SourcewindowX" ) ); + r.setY( config.readNumEntry( keybase + "Geometry/SourcewindowY" ) ); + r.setWidth( config.readNumEntry( keybase + + "Geometry/SourcewindowWidth" ) ); + r.setHeight( config.readNumEntry( keybase + + "Geometry/SourcewindowHeight" ) ); + if ( place == TQDockWindow::OutsideDock ) { + dw->undock(); + dw->show(); + } + dw->setGeometry( r ); + + dw = (TQDockWindow *) plv->parent()->parent(); + place = config.readNumEntry( keybase + "Geometry/PhrasewindowInDock" ); + r.setX( config.readNumEntry( keybase + "Geometry/PhrasewindowX" ) ); + r.setY( config.readNumEntry( keybase + "Geometry/PhrasewindowY" ) ); + r.setWidth( config.readNumEntry( keybase + + "Geometry/PhrasewindowWidth" ) ); + r.setHeight( config.readNumEntry( keybase + + "Geometry/PhrasewindowHeight" ) ); + if ( place == TQDockWindow::OutsideDock ) { + dw->undock(); + dw->show(); + } + dw->setGeometry( r ); + TQApplication::sendPostedEvents(); +} + +void TrWindow::writeConfig() +{ + TQString keybase( "/TQt Linguist/" + + TQString::number( (QT_VERSION >> 16) & 0xff ) + + "." + TQString::number( (QT_VERSION >> 8) & 0xff ) + "/" ); + TQSettings config; + + config.insertSearchPath( TQSettings::Windows, "/Trolltech" ); + config.writeEntry( keybase + "RecentlyOpenedFiles", recentFiles ); + config.writeEntry( keybase + "Geometry/MainwindowMaximized", isMaximized() ); + config.writeEntry( keybase + "Geometry/MainwindowX", x() ); + config.writeEntry( keybase + "Geometry/MainwindowY", y() ); + config.writeEntry( keybase + "Geometry/MainwindowWidth", width() ); + config.writeEntry( keybase + "Geometry/MainwindowHeight", height() ); + + TQDockWindow * dw =(TQDockWindow *) lv->parent(); + config.writeEntry( keybase + "Geometry/ContextwindowInDock", dw->place() ); + config.writeEntry( keybase + "Geometry/ContextwindowX", dw->x() ); + config.writeEntry( keybase + "Geometry/ContextwindowY", dw->y() ); + config.writeEntry( keybase + "Geometry/ContextwindowWidth", dw->width() ); + config.writeEntry( keybase + "Geometry/ContextwindowHeight", dw->height() ); + + dw =(TQDockWindow *) slv->parent(); + config.writeEntry( keybase + "Geometry/SourcewindowInDock", + dw->place() ); + config.writeEntry( keybase + "Geometry/SourcewindowX", dw->geometry().x() ); + config.writeEntry( keybase + "Geometry/SourcewindowY", dw->geometry().y() ); + config.writeEntry( keybase + "Geometry/SourcewindowWidth", dw->width() ); + config.writeEntry( keybase + "Geometry/SourcewindowHeight", dw->height() ); + + dw =(TQDockWindow *) plv->parent()->parent(); + config.writeEntry( keybase + "Geometry/PhrasewindowInDock", + dw->place() ); + config.writeEntry( keybase + "Geometry/PhrasewindowX", dw->geometry().x() ); + config.writeEntry( keybase + "Geometry/PhrasewindowY", dw->geometry().y() ); + config.writeEntry( keybase + "Geometry/PhrasewindowWidth", dw->width() ); + config.writeEntry( keybase + "Geometry/PhrasewindowHeight", dw->height() ); +} + +void TrWindow::setupRecentFilesMenu() +{ + recentFilesMenu->clear(); + int id = 0; + TQStringList::Iterator it = recentFiles.begin(); + for ( ; it != recentFiles.end(); ++it ) + { + recentFilesMenu->insertItem( *it, id ); + id++; + } +} + +void TrWindow::recentFileActivated( int id ) +{ + if ( id != -1 ) { + if ( maybeSave() ) + openFile( *recentFiles.at( id ) ); + } +} + +void TrWindow::addRecentlyOpenedFile( const TQString &fn, TQStringList &lst ) +{ + if ( lst.find( fn ) != lst.end() ) + return; + if ( lst.count() >= 10 ) + lst.remove( lst.begin() ); + lst << fn; +} + +void TrWindow::toggleGuessing() +{ + me->toggleGuessing(); +} + +void TrWindow::focusSourceList() +{ + slv->setFocus(); +} + +void TrWindow::focusPhraseList() +{ + plv->setFocus(); +} + +void TrWindow::updateClosePhraseBook() +{ + if ( dirtyItem != -1 ) { + closePhraseBookp->removeItem( closePhraseBookp->idAt(dirtyItem) ); + dirtyItem = -1; + } +} + +void TrWindow::toggleStatistics() +{ + if ( toggleStats->isOn() ) { + if ( !stats ) { + stats = new Statistics( this, "linguist_stats" ); + connect( this, SIGNAL(statsChanged(int,int,int,int,int,int)), stats, + SLOT(updateStats(int,int,int,int,int,int)) ); + connect( stats, SIGNAL(closed()), toggleStats, SLOT(toggle()) ); + } + updateStatistics(); + stats->show(); + } else if ( stats ) { + stats->close(); + } +} + +void TrWindow::updateStatistics() +{ + TQListViewItem * ci = lv->firstChild(); + int trW = 0; + int trC = 0; + int trCS = 0; + while ( ci ) { + countStats( ci, ((ContextLVI *)ci)->firstMessageItem(), trW, trC, trCS ); + ci = ci->nextSibling(); + } + // ..and the items in the source list + countStats( 0, slv->firstChild(), trW, trC, trCS ); + emit statsChanged( srcWords, srcChars, srcCharsSpc, trW, trC, trCS ); +} + + +void TrWindow::countStats( TQListViewItem* ci, TQListViewItem* mi, int& trW, int& trC, int& trCS ) +{ + MessageLVI * m; + while ( mi ) { + m = (MessageLVI *) mi; + if ( m->finished() && !(m->message().type() == MetaTranslatorMessage::Obsolete) ) + doCharCounting( m->translation(), trW, trC, trCS ); + if ( ci ) + mi = ((ContextLVI *)ci)->nextMessageItem(); + else + mi = mi->nextSibling(); + } +} + +void TrWindow::doCharCounting( const TQString& text, int& trW, int& trC, int& trCS ) +{ + trCS += text.length(); + bool inWord = FALSE; + for ( int i = 0; i < (int) text.length(); i++ ) { + if ( text[i].isLetterOrNumber() || text[i] == TQChar('_') ) { + if ( !inWord ) { + trW++; + inWord = TRUE; + } + } else { + inWord = FALSE; + } + if ( !text[i].isSpace() ) + trC++; + } +} diff --git a/tools/linguist/linguist/trwindow.h b/tools/linguist/linguist/trwindow.h new file mode 100644 index 000000000..439ce7cba --- /dev/null +++ b/tools/linguist/linguist/trwindow.h @@ -0,0 +1,237 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef TRWINDOW_H +#define TRWINDOW_H + +#include "phrase.h" + +#include + +#include +#include +#include +#include +#include +#include +#include + +class TQAction; +class TQDialog; +class TQLabel; +class TQListView; +class TQListViewItem; +class TQPrinter; + +class Action; +class FindDialog; +class MessageEditor; + +class PhraseLV; +class ContextLVI; +class Statistics; + +class TrWindow : public TQMainWindow +{ + Q_OBJECT +public: + static TQPixmap * pxOn; + static TQPixmap * pxOff; + static TQPixmap * pxObsolete; + static TQPixmap * pxDanger; + static const TQPixmap pageCurl(); + + TrWindow(); + ~TrWindow(); + + void openFile( const TQString& name ); + +protected: + void readConfig(); + void writeConfig(); + void closeEvent( TQCloseEvent * ); + +signals: + void statsChanged( int w, int c, int cs, int w2, int c2, int cs2 ); + +private slots: + void doneAndNext(); + void prev(); + void next(); + void recentFileActivated( int ); + void setupRecentFilesMenu(); + void open(); + void save(); + void saveAs(); + void release(); + void print(); + void find(); + void findAgain(); + void replace(); + void newPhraseBook(); + void openPhraseBook(); + void closePhraseBook( int id ); + void editPhraseBook( int id ); + void printPhraseBook( int id ); + void manual(); + void revertSorting(); + void about(); + void aboutTQt(); + + void setupPhrase(); + bool maybeSave(); + void updateCaption(); + void showNewScope( TQListViewItem *item ); + void showNewCurrent( TQListViewItem *item ); + void updateTranslation( const TQString& translation ); + void updateFinished( bool finished ); + void toggleFinished( TQListViewItem *item, const TQPoint& p, int column ); + void prevUnfinished(); + void nextUnfinished(); + void findNext( const TQString& text, int where, bool matchCase ); + void revalidate(); + void toggleGuessing(); + void focusSourceList(); + void focusPhraseList(); + void updateClosePhraseBook(); + void toggleStatistics(); + void updateStatistics(); + +private: + typedef TQPtrList PBL; + typedef TQDict PBD; + + static TQString friendlyString( const TQString& str ); + + void addRecentlyOpenedFile( const TQString & fn, TQStringList & lst ); + void setupMenuBar(); + void setupToolBars(); + void setCurrentContextItem( TQListViewItem *item ); + void setCurrentMessageItem( TQListViewItem *item ); + TQString friendlyPhraseBookName( int k ); + bool openPhraseBook( const TQString& name ); + bool savePhraseBook( TQString& name, const PhraseBook& pb ); + void updateProgress(); + void updatePhraseDict(); + PhraseBook getPhrases( const TQString& source ); + bool danger( const TQString& source, const TQString& translation, + bool verbose = FALSE ); + + int itemToIndex( TQListView * view, TQListViewItem * item ); + TQListViewItem * indexToItem( TQListView * view, int index ); + bool searchItem( const TQString & searchWhat, TQListViewItem * j, + TQListViewItem * k ); + void countStats( TQListViewItem * ci, TQListViewItem * mi, int& trW, int& trC, int& trCS ); + void doCharCounting( const TQString& text, int& trW, int& trC, int& trCS ); + + TQListView * plv; + TQListView * lv; + TQListView * slv; + MessageEditor * me; + TQLabel * progress; + TQLabel * modified; + MetaTranslator tor; + bool dirty; + bool messageIsShown; + int numFinished; + int numNonobsolete; + int numMessages; + int dirtyItem; + TQStringList recentFiles; + TQString filename; + + PBD phraseDict; + PBL phraseBooks; + TQStringList phraseBookNames; + + TQPrinter printer; + + FindDialog *f; + FindDialog *h; + TQString findText; + int findWhere; + bool findMatchCase; + int foundItem; + TQListViewItem *foundScope; + int foundWhere; + int foundOffset; + + TQPopupMenu * phrasep; + TQPopupMenu * closePhraseBookp; + TQPopupMenu * editPhraseBookp; + TQPopupMenu * printPhraseBookp; + TQPopupMenu * recentFilesMenu; + int closePhraseBookId; + int editPhraseBookId; + int printPhraseBookId; + Action *openAct; + Action *saveAct; + Action *saveAsAct; + Action *releaseAct; + Action *printAct; + Action *exitAct; + Action *undoAct; + Action *redoAct; + Action *cutAct; + Action *copyAct; + Action *pasteAct; + Action *selectAllAct; + Action *findAct; + Action *findAgainAct; + Action *replaceAct; + Action *newPhraseBookAct; + Action *openPhraseBookAct; + Action *acceleratorsAct; + Action *endingPunctuationAct; + Action *phraseMatchesAct; + Action *revertSortingAct; + Action *aboutAct; + Action *aboutTQtAct; + Action *manualAct; + Action *whatsThisAct; + Action *beginFromSourceAct; + Action *prevAct; + Action *nextAct; + Action *prevUnfinishedAct; + Action *nextUnfinishedAct; + Action *doneAndNextAct; + TQAction *doneAndNextAlt; + Action *doGuessesAct; + Action *toggleStats; + Statistics * stats; + int srcWords; + int srcChars; + int srcCharsSpc; +}; + +#endif diff --git a/tools/linguist/lrelease/lrelease.pro b/tools/linguist/lrelease/lrelease.pro new file mode 100644 index 000000000..755ea46a0 --- /dev/null +++ b/tools/linguist/lrelease/lrelease.pro @@ -0,0 +1,17 @@ +TEMPLATE = app +CONFIG += qt warn_on console +HEADERS = ../shared/metatranslator.h \ + ../shared/proparser.h +SOURCES = main.cpp \ + ../shared/metatranslator.cpp \ + ../shared/proparser.cpp + +DEFINES += QT_INTERNAL_XML +include( ../../../src/qt_professional.pri ) + +TARGET = lrelease +INCLUDEPATH += ../shared +DESTDIR = ../../../bin + +target.path=$$bins.path +INSTALLS += target diff --git a/tools/linguist/lrelease/main.cpp b/tools/linguist/lrelease/main.cpp new file mode 100644 index 000000000..f939ccf4e --- /dev/null +++ b/tools/linguist/lrelease/main.cpp @@ -0,0 +1,203 @@ +/********************************************************************** +** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include + +typedef TQValueList TML; + +static void printUsage() +{ + fprintf( stderr, "Usage:\n" + " lrelease [options] project-file\n" + " lrelease [options] ts-files [-qm qm-file]\n" + "Options:\n" + " -help Display this information and exit\n" + " -nocompress\n" + " Do not compress the .qm files\n" + " -verbose\n" + " Explain what is being done\n" + " -version\n" + " Display the version of lrelease and exit\n" ); +} + +static bool loadTsFile( MetaTranslator& tor, const TQString& tsFileName, + bool /* verbose */ ) +{ + TQString qmFileName = tsFileName; + qmFileName.replace( TQRegExp("\\.ts$"), "" ); + qmFileName += ".qm"; + + bool ok = tor.load( tsFileName ); + if ( !ok ) + fprintf( stderr, + "lrelease warning: For some reason, I cannot load '%s'\n", + tsFileName.latin1() ); + return ok; +} + +static void releaseMetaTranslator( const MetaTranslator& tor, + const TQString& qmFileName, bool verbose, + bool stripped ) +{ + if ( verbose ) + fprintf( stderr, "Updating '%s'...\n", qmFileName.latin1() ); + if ( !tor.release(qmFileName, verbose, + stripped ? TQTranslator::Stripped + : TQTranslator::Everything) ) + fprintf( stderr, + "lrelease warning: For some reason, I cannot save '%s'\n", + qmFileName.latin1() ); +} + +static void releaseTsFile( const TQString& tsFileName, bool verbose, + bool stripped ) +{ + MetaTranslator tor; + if ( loadTsFile(tor, tsFileName, verbose) ) { + TQString qmFileName = tsFileName; + qmFileName.replace( TQRegExp("\\.ts$"), "" ); + qmFileName += ".qm"; + releaseMetaTranslator( tor, qmFileName, verbose, stripped ); + } +} + +int main( int argc, char **argv ) +{ + bool verbose = FALSE; + bool stripped = TRUE; + bool metTranslations = FALSE; + MetaTranslator tor; + TQString outputFile; + int numFiles = 0; + int i; + + for ( i = 1; i < argc; i++ ) { + if ( qstrcmp(argv[i], "-nocompress") == 0 ) { + stripped = FALSE; + continue; + } else if ( qstrcmp(argv[i], "-verbose") == 0 ) { + verbose = TRUE; + continue; + } else if ( qstrcmp(argv[i], "-version") == 0 ) { + fprintf( stderr, "lrelease version %s\n", QT_VERSION_STR ); + return 0; + } else if ( qstrcmp(argv[i], "-qm") == 0 ) { + if ( i == argc - 1 ) { + printUsage(); + return 1; + } else { + i++; + outputFile = argv[i]; + argv[i][0] = '-'; + } + } else if ( qstrcmp(argv[i], "-help") == 0 ) { + printUsage(); + return 0; + } else if ( argv[i][0] == '-' ) { + printUsage(); + return 1; + } else { + numFiles++; + } + } + + if ( numFiles == 0 ) { + printUsage(); + return 1; + } + + for ( i = 1; i < argc; i++ ) { + if ( argv[i][0] == '-' ) + continue; + + TQFile f( argv[i] ); + if ( !f.open(IO_ReadOnly) ) { + fprintf( stderr, + "lrelease error: Cannot open file '%s': %s\n", argv[i], + strerror(errno) ); + return 1; + } + + TQTextStream t( &f ); + TQString fullText = t.read(); + f.close(); + + if ( fullText.find(TQString("")) >= 0 ) { + if ( outputFile.isEmpty() ) { + releaseTsFile( argv[i], verbose, stripped ); + } else { + loadTsFile( tor, argv[i], verbose ); + } + } else { + TQString oldDir = TQDir::currentDirPath(); + TQDir::setCurrent( TQFileInfo(argv[i]).dirPath() ); + + TQMap tagMap = proFileTagMap( fullText ); + TQMap::Iterator it; + + for ( it = tagMap.begin(); it != tagMap.end(); ++it ) { + TQStringList toks = TQStringList::split( ' ', it.data() ); + TQStringList::Iterator t; + + for ( t = toks.begin(); t != toks.end(); ++t ) { + if ( it.key() == TQString("TRANSLATIONS") ) { + metTranslations = TRUE; + releaseTsFile( *t, verbose, stripped ); + } + } + } + if ( !metTranslations ) + fprintf( stderr, + "lrelease warning: Met no 'TRANSLATIONS' entry in" + " project file '%s'\n", + argv[i] ); + TQDir::setCurrent( oldDir ); + } + } + + if ( !outputFile.isEmpty() ) + releaseMetaTranslator( tor, outputFile, verbose, stripped ); + + return 0; +} diff --git a/tools/linguist/lupdate/fetchtr.cpp b/tools/linguist/lupdate/fetchtr.cpp new file mode 100644 index 000000000..e2702a492 --- /dev/null +++ b/tools/linguist/lupdate/fetchtr.cpp @@ -0,0 +1,824 @@ +/********************************************************************** +** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +/* qmake ignore Q_OBJECT */ + +static const char MagicComment[] = "TRANSLATOR "; + +static TQMap needs_Q_OBJECT; +static TQMap lacks_Q_OBJECT; + +/* + The first part of this source file is the C++ tokenizer. We skip + most of C++; the only tokens that interest us are defined here. + Thus, the code fragment + + int main() + { + printf( "Hello, world!\n" ); + return 0; + } + + is broken down into the following tokens (Tok_ omitted): + + Ident Ident LeftParen RightParen + LeftBrace + Ident LeftParen String RightParen Semicolon + return Semicolon + RightBrace. + + The 0 doesn't produce any token. +*/ + +enum { Tok_Eof, Tok_class, Tok_namespace, Tok_return, Tok_tr, + Tok_trUtf8, Tok_translate, Tok_Q_OBJECT, Tok_Ident, + Tok_Comment, Tok_String, Tok_Arrow, Tok_Colon, + Tok_Gulbrandsen, Tok_LeftBrace, Tok_RightBrace, Tok_LeftParen, + Tok_RightParen, Tok_Comma, Tok_Semicolon }; + +/* + The tokenizer maintains the following global variables. The names + should be self-explanatory. +*/ +static TQCString yyFileName; +static int yyCh; +static char yyIdent[128]; +static size_t yyIdentLen; +static char yyComment[65536]; +static size_t yyCommentLen; +static char yyString[65536]; +static size_t yyStringLen; +static TQValueStack yySavedBraceDepth; +static TQValueStack yySavedParenDepth; +static int yyBraceDepth; +static int yyParenDepth; +static int yyLineNo; +static int yyCurLineNo; +static int yyBraceLineNo; +static int yyParenLineNo; + +// the file to read from (if reading from a file) +static FILE *yyInFile; + +// the string to read from and current position in the string (otherwise) +static TQString yyInStr; +static int yyInPos; + +static int (*getChar)(); + +static int getCharFromFile() +{ + int c = getc( yyInFile ); + if ( c == '\n' ) + yyCurLineNo++; + return c; +} + +static int getCharFromString() +{ + if ( yyInPos == (int) yyInStr.length() ) { + return EOF; + } else { + return yyInStr[yyInPos++].latin1(); + } +} + +static void startTokenizer( const char *fileName, int (*getCharFunc)() ) +{ + yyInPos = 0; + getChar = getCharFunc; + + yyFileName = fileName; + yyCh = getChar(); + yySavedBraceDepth.clear(); + yySavedParenDepth.clear(); + yyBraceDepth = 0; + yyParenDepth = 0; + yyCurLineNo = 1; + yyBraceLineNo = 1; + yyParenLineNo = 1; +} + +static int getToken() +{ + const char tab[] = "abfnrtv"; + const char backTab[] = "\a\b\f\n\r\t\v"; + uint n; + + yyIdentLen = 0; + yyCommentLen = 0; + yyStringLen = 0; + + while ( yyCh != EOF ) { + yyLineNo = yyCurLineNo; + + if ( isalpha(yyCh) || yyCh == '_' ) { + do { + if ( yyIdentLen < sizeof(yyIdent) - 1 ) + yyIdent[yyIdentLen++] = (char) yyCh; + yyCh = getChar(); + } while ( isalnum(yyCh) || yyCh == '_' ); + yyIdent[yyIdentLen] = '\0'; + + switch ( yyIdent[0] ) { + case 'Q': + if ( strcmp(yyIdent + 1, "_OBJECT") == 0 ) { + return Tok_Q_OBJECT; + } else if ( strcmp(yyIdent + 1, "T_TR_NOOP") == 0 ) { + return Tok_tr; + } else if ( strcmp(yyIdent + 1, "T_TRANSLATE_NOOP") == 0 ) { + return Tok_translate; + } + break; + case 'T': + // TR() for when all else fails + if ( qstricmp(yyIdent + 1, "R") == 0 ) + return Tok_tr; + break; + case 'c': + if ( strcmp(yyIdent + 1, "lass") == 0 ) + return Tok_class; + break; + case 'f': + /* + TQTranslator::findMessage() has the same parameters as + TQApplication::translate(). + */ + if ( strcmp(yyIdent + 1, "indMessage") == 0 ) + return Tok_translate; + break; + case 'n': + if ( strcmp(yyIdent + 1, "amespace") == 0 ) + return Tok_namespace; + break; + case 'r': + if ( strcmp(yyIdent + 1, "eturn") == 0 ) + return Tok_return; + break; + case 's': + if ( strcmp(yyIdent + 1, "truct") == 0 ) + return Tok_class; + break; + case 't': + if ( strcmp(yyIdent + 1, "r") == 0 ) { + return Tok_tr; + } else if ( qstrcmp(yyIdent + 1, "rUtf8") == 0 ) { + return Tok_trUtf8; + } else if ( qstrcmp(yyIdent + 1, "ranslate") == 0 ) { + return Tok_translate; + } + } + return Tok_Ident; + } else { + switch ( yyCh ) { + case '#': + /* + Early versions of lupdate complained about + unbalanced braces in the following code: + + #ifdef ALPHA + while ( beta ) { + #else + while ( gamma ) { + #endif + delta; + } + + The code contains, indeed, two opening braces for + one closing brace; yet there's no reason to panic. + + The solution is to remember yyBraceDepth as it was + when #if, #ifdef or #ifndef was met, and to set + yyBraceDepth to that value when meeting #elif or + #else. + */ + do { + yyCh = getChar(); + } while ( isspace(yyCh) && yyCh != '\n' ); + + switch ( yyCh ) { + case 'i': + yyCh = getChar(); + if ( yyCh == 'f' ) { + // if, ifdef, ifndef + yySavedBraceDepth.push( yyBraceDepth ); + yySavedParenDepth.push( yyParenDepth ); + } + break; + case 'e': + yyCh = getChar(); + if ( yyCh == 'l' ) { + // elif, else + if ( !yySavedBraceDepth.isEmpty() ) { + yyBraceDepth = yySavedBraceDepth.top(); + yyParenDepth = yySavedParenDepth.top(); + } + } else if ( yyCh == 'n' ) { + // endif + if ( !yySavedBraceDepth.isEmpty() ) { + yySavedBraceDepth.pop(); + yySavedParenDepth.pop(); + } + } + } + while ( isalnum(yyCh) || yyCh == '_' ) + yyCh = getChar(); + break; + case '/': + yyCh = getChar(); + if ( yyCh == '/' ) { + do { + yyCh = getChar(); + } while ( yyCh != EOF && yyCh != '\n' ); + } else if ( yyCh == '*' ) { + bool metAster = FALSE; + bool metAsterSlash = FALSE; + + while ( !metAsterSlash ) { + yyCh = getChar(); + if ( yyCh == EOF ) { + fprintf( stderr, + "%s: Unterminated C++ comment starting at" + " line %d\n", + (const char *) yyFileName, yyLineNo ); + yyComment[yyCommentLen] = '\0'; + return Tok_Comment; + } + if ( yyCommentLen < sizeof(yyComment) - 1 ) + yyComment[yyCommentLen++] = (char) yyCh; + + if ( yyCh == '*' ) + metAster = TRUE; + else if ( metAster && yyCh == '/' ) + metAsterSlash = TRUE; + else + metAster = FALSE; + } + yyCh = getChar(); + yyCommentLen -= 2; + yyComment[yyCommentLen] = '\0'; + return Tok_Comment; + } + break; + case '"': + yyCh = getChar(); + + while ( yyCh != EOF && yyCh != '\n' && yyCh != '"' ) { + if ( yyCh == '\\' ) { + yyCh = getChar(); + + if ( yyCh == '\n' ) { + yyCh = getChar(); + } else if ( yyCh == 'x' ) { + TQCString hex = "0"; + + yyCh = getChar(); + while ( isxdigit(yyCh) ) { + hex += (char) yyCh; + yyCh = getChar(); + } + sscanf( hex, "%x", &n ); + if ( yyStringLen < sizeof(yyString) - 1 ) + yyString[yyStringLen++] = (char) n; + } else if ( yyCh >= '0' && yyCh < '8' ) { + TQCString oct = ""; + + do { + oct += (char) yyCh; + yyCh = getChar(); + } while ( yyCh >= '0' && yyCh < '8' ); + sscanf( oct, "%o", &n ); + if ( yyStringLen < sizeof(yyString) - 1 ) + yyString[yyStringLen++] = (char) n; + } else { + const char *p = strchr( tab, yyCh ); + if ( yyStringLen < sizeof(yyString) - 1 ) + yyString[yyStringLen++] = ( p == 0 ) ? + (char) yyCh : backTab[p - tab]; + yyCh = getChar(); + } + } else { + if ( yyStringLen < sizeof(yyString) - 1 ) + yyString[yyStringLen++] = (char) yyCh; + yyCh = getChar(); + } + } + yyString[yyStringLen] = '\0'; + + if ( yyCh != '"' ) + qWarning( "%s:%d: Unterminated C++ string", + (const char *) yyFileName, yyLineNo ); + + if ( yyCh == EOF ) { + return Tok_Eof; + } else { + yyCh = getChar(); + return Tok_String; + } + break; + case '-': + yyCh = getChar(); + if ( yyCh == '>' ) { + yyCh = getChar(); + return Tok_Arrow; + } + break; + case ':': + yyCh = getChar(); + if ( yyCh == ':' ) { + yyCh = getChar(); + return Tok_Gulbrandsen; + } + return Tok_Colon; + case '\'': + yyCh = getChar(); + if ( yyCh == '\\' ) + yyCh = getChar(); + + do { + yyCh = getChar(); + } while ( yyCh != EOF && yyCh != '\'' ); + yyCh = getChar(); + break; + case '{': + if (yyBraceDepth == 0) + yyBraceLineNo = yyCurLineNo; + yyBraceDepth++; + yyCh = getChar(); + return Tok_LeftBrace; + case '}': + if (yyBraceDepth == 0) + yyBraceLineNo = yyCurLineNo; + yyBraceDepth--; + yyCh = getChar(); + return Tok_RightBrace; + case '(': + if (yyParenDepth == 0) + yyParenLineNo = yyCurLineNo; + yyParenDepth++; + yyCh = getChar(); + return Tok_LeftParen; + case ')': + if (yyParenDepth == 0) + yyParenLineNo = yyCurLineNo; + yyParenDepth--; + yyCh = getChar(); + return Tok_RightParen; + case ',': + yyCh = getChar(); + return Tok_Comma; + case ';': + yyCh = getChar(); + return Tok_Semicolon; + default: + yyCh = getChar(); + } + } + } + return Tok_Eof; +} + +/* + The second part of this source file is the parser. It accomplishes + a very easy task: It finds all strings inside a tr() or translate() + call, and possibly finds out the context of the call. It supports + three cases: (1) the context is specified, as in + FunnyDialog::tr("Hello") or translate("FunnyDialog", "Hello"); + (2) the call appears within an inlined function; (3) the call + appears within a function defined outside the class definition. +*/ + +static int yyTok; + +static bool match( int t ) +{ + bool matches = ( yyTok == t ); + if ( matches ) + yyTok = getToken(); + return matches; +} + +static bool matchString( TQCString *s ) +{ + bool matches = ( yyTok == Tok_String ); + *s = ""; + while ( yyTok == Tok_String ) { + *s += yyString; + yyTok = getToken(); + } + return matches; +} + +static bool matchEncoding( bool *utf8 ) +{ + if ( yyTok == Tok_Ident ) { + if ( strcmp(yyIdent, "TQApplication") == 0 ) { + yyTok = getToken(); + if ( yyTok == Tok_Gulbrandsen ) + yyTok = getToken(); + } + *utf8 = TQString( yyIdent ).endsWith( TQString("UTF8") ); + yyTok = getToken(); + return TRUE; + } else { + return FALSE; + } +} + +static void parse( MetaTranslator *tor, const char *initialContext, + const char *defaultContext ) +{ + TQMap qualifiedContexts; + TQStringList namespaces; + TQCString context; + TQCString text; + TQCString com; + TQCString functionContext = initialContext; + TQCString prefix; + bool utf8 = FALSE; + bool missing_Q_OBJECT = FALSE; + + yyTok = getToken(); + while ( yyTok != Tok_Eof ) { + switch ( yyTok ) { + case Tok_class: + /* + Partial support for inlined functions. + */ + yyTok = getToken(); + if ( yyBraceDepth == (int) namespaces.count() && + yyParenDepth == 0 ) { + do { + /* + This code should execute only once, but we play + safe with impure definitions such as + 'class Q_EXPORT TQMessageBox', in which case + 'TQMessageBox' is the class name, not 'Q_EXPORT'. + */ + functionContext = yyIdent; + yyTok = getToken(); + } while ( yyTok == Tok_Ident ); + + while ( yyTok == Tok_Gulbrandsen ) { + yyTok = getToken(); + functionContext += "::"; + functionContext += yyIdent; + yyTok = getToken(); + } + + if ( yyTok == Tok_Colon ) { + missing_Q_OBJECT = TRUE; + } else { + functionContext = defaultContext; + } + } + break; + case Tok_namespace: + yyTok = getToken(); + if ( yyTok == Tok_Ident ) { + TQCString ns = yyIdent; + yyTok = getToken(); + if ( yyTok == Tok_LeftBrace && + yyBraceDepth == (int) namespaces.count() + 1 ) + namespaces.append( TQString(ns) ); + } + break; + case Tok_tr: + case Tok_trUtf8: + utf8 = ( yyTok == Tok_trUtf8 ); + yyTok = getToken(); + if ( match(Tok_LeftParen) && matchString(&text) ) { + com = ""; + if ( match(Tok_RightParen) || (match(Tok_Comma) && + matchString(&com) && match(Tok_RightParen)) ) { + if ( prefix.isNull() ) { + context = functionContext; + if ( !namespaces.isEmpty() ) + context.prepend( (namespaces.join(TQString("::")) + + TQString("::")).latin1() ); + } else { + context = prefix; + } + prefix = (const char *) 0; + + if ( qualifiedContexts.contains(context) ) + context = qualifiedContexts[context]; + tor->insert( MetaTranslatorMessage(context, text, com, + TQString::null, utf8) ); + + if ( lacks_Q_OBJECT.contains(context) ) { + qWarning( "%s:%d: Class '%s' lacks Q_OBJECT macro", + (const char *) yyFileName, yyLineNo, + (const char *) context ); + lacks_Q_OBJECT.remove( context ); + } else { + needs_Q_OBJECT.insert( context, 0 ); + } + } + } + break; + case Tok_translate: + utf8 = FALSE; + yyTok = getToken(); + if ( match(Tok_LeftParen) && + matchString(&context) && + match(Tok_Comma) && + matchString(&text) ) { + com = ""; + if ( match(Tok_RightParen) || + (match(Tok_Comma) && + matchString(&com) && + (match(Tok_RightParen) || + match(Tok_Comma) && + matchEncoding(&utf8) && + match(Tok_RightParen))) ) + tor->insert( MetaTranslatorMessage(context, text, com, + TQString::null, utf8) ); + } + break; + case Tok_Q_OBJECT: + missing_Q_OBJECT = FALSE; + yyTok = getToken(); + break; + case Tok_Ident: + if ( !prefix.isNull() ) + prefix += "::"; + prefix += yyIdent; + yyTok = getToken(); + if ( yyTok != Tok_Gulbrandsen ) + prefix = (const char *) 0; + break; + case Tok_Comment: + com = yyComment; + com = com.simplifyWhiteSpace(); + if ( com.left(sizeof(MagicComment) - 1) == MagicComment ) { + com.remove( 0, sizeof(MagicComment) - 1 ); + int k = com.find( ' ' ); + if ( k == -1 ) { + context = com; + } else { + context = com.left( k ); + com.remove( 0, k + 1 ); + tor->insert( MetaTranslatorMessage(context, "", com, + TQString::null, FALSE) ); + } + + /* + Provide a backdoor for people using "using + namespace". See the manual for details. + */ + k = 0; + while ( (k = context.find("::", k)) != -1 ) { + qualifiedContexts.insert( context.mid(k + 2), context ); + k++; + } + } + yyTok = getToken(); + break; + case Tok_Arrow: + yyTok = getToken(); + if ( yyTok == Tok_tr || yyTok == Tok_trUtf8 ) + qWarning( "%s:%d: Cannot invoke tr() like this", + (const char *) yyFileName, yyLineNo ); + break; + case Tok_Gulbrandsen: + // at top level? + if ( yyBraceDepth == (int) namespaces.count() && yyParenDepth == 0 ) + functionContext = prefix; + yyTok = getToken(); + break; + case Tok_RightBrace: + case Tok_Semicolon: + if ( yyBraceDepth >= 0 && + yyBraceDepth + 1 == (int) namespaces.count() ) + namespaces.remove( namespaces.fromLast() ); + if ( yyBraceDepth == (int) namespaces.count() ) { + if ( missing_Q_OBJECT ) { + if ( needs_Q_OBJECT.contains(functionContext) ) { + qWarning( "%s:%d: Class '%s' lacks Q_OBJECT macro", + (const char *) yyFileName, yyLineNo, + (const char *) functionContext ); + } else { + lacks_Q_OBJECT.insert( functionContext, 0 ); + } + } + functionContext = defaultContext; + missing_Q_OBJECT = FALSE; + } + yyTok = getToken(); + break; + default: + yyTok = getToken(); + } + } + + if ( yyBraceDepth != 0 ) + fprintf( stderr, + "%s:%d: Unbalanced braces in C++ code (or abuse of the C++" + " preprocessor)\n", + (const char *)yyFileName, yyBraceLineNo ); + else if ( yyParenDepth != 0 ) + fprintf( stderr, + "%s:%d: Unbalanced parentheses in C++ code (or abuse of the C++" + " preprocessor)\n", + (const char *)yyFileName, yyParenLineNo ); +} + +void fetchtr_cpp( const char *fileName, MetaTranslator *tor, + const char *defaultContext, bool mustExist ) +{ + yyInFile = fopen( fileName, "r" ); + if ( yyInFile == 0 ) { + if ( mustExist ) + fprintf( stderr, + "lupdate error: Cannot open C++ source file '%s': %s\n", + fileName, strerror(errno) ); + return; + } + + startTokenizer( fileName, getCharFromFile ); + parse( tor, 0, defaultContext ); + fclose( yyInFile ); +} + +/* + In addition to C++, we support TQt Designer UI files. +*/ + +/* + Fetches tr() calls in C++ code in UI files (inside "" + tag). This mechanism is obsolete. +*/ +void fetchtr_inlined_cpp( const char *fileName, const TQString& in, + MetaTranslator *tor, const char *context ) +{ + yyInStr = in; + startTokenizer( fileName, getCharFromString ); + parse( tor, context, 0 ); + yyInStr = TQString::null; +} + +class UiHandler : public TQXmlDefaultHandler +{ +public: + UiHandler( MetaTranslator *translator, const char *fileName ) + : tor( translator ), fname( fileName ), comment( "" ) { } + + virtual bool startElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName, + const TQXmlAttributes& atts ); + virtual bool endElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName ); + virtual bool characters( const TQString& ch ); + virtual bool fatalError( const TQXmlParseException& exception ); + +private: + void flush(); + + MetaTranslator *tor; + TQCString fname; + TQString context; + TQString source; + TQString comment; + + TQString accum; +}; + +bool UiHandler::startElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName, + const TQXmlAttributes& atts ) +{ + if ( qName == TQString("item") ) { + flush(); + if ( !atts.value(TQString("text")).isEmpty() ) + source = atts.value( TQString("text") ); + } else if ( qName == TQString("string") ) { + flush(); + } + accum.truncate( 0 ); + return TRUE; +} + +bool UiHandler::endElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName ) +{ + accum.replace( TQRegExp(TQString("\r\n")), "\n" ); + + if ( qName == TQString("class") ) { + if ( context.isEmpty() ) + context = accum; + } else if ( qName == TQString("string") ) { + source = accum; + } else if ( qName == TQString("comment") ) { + comment = accum; + flush(); + } else if ( qName == TQString("function") ) { + fetchtr_inlined_cpp( (const char *) fname, accum, tor, + context.latin1() ); + } else { + flush(); + } + return TRUE; +} + +bool UiHandler::characters( const TQString& ch ) +{ + accum += ch; + return TRUE; +} + +bool UiHandler::fatalError( const TQXmlParseException& exception ) +{ + TQString msg; + msg.sprintf( "Parse error at line %d, column %d (%s).", + exception.lineNumber(), exception.columnNumber(), + exception.message().latin1() ); + fprintf( stderr, "XML error: %s\n", msg.latin1() ); + return FALSE; +} + +void UiHandler::flush() +{ + if ( !context.isEmpty() && !source.isEmpty() ) + tor->insert( MetaTranslatorMessage(context.utf8(), source.utf8(), + comment.utf8(), TQString::null, + TRUE) ); + source.truncate( 0 ); + comment.truncate( 0 ); +} + +void fetchtr_ui( const char *fileName, MetaTranslator *tor, + const char * /* defaultContext */, bool mustExist ) +{ + TQFile f( fileName ); + if ( !f.open(IO_ReadOnly) ) { + if ( mustExist ) + fprintf( stderr, "lupdate error: cannot open UI file '%s': %s\n", + fileName, strerror(errno) ); + return; + } + + TQTextStream t( &f ); + TQXmlInputSource in( t ); + TQXmlSimpleReader reader; + reader.setFeature( "http://xml.org/sax/features/namespaces", FALSE ); + reader.setFeature( "http://xml.org/sax/features/namespace-prefixes", TRUE ); + reader.setFeature( "http://trolltech.com/xml/features/report-whitespace" + "-only-CharData", FALSE ); + TQXmlDefaultHandler *hand = new UiHandler( tor, fileName ); + reader.setContentHandler( hand ); + reader.setErrorHandler( hand ); + + if ( !reader.parse(in) ) + fprintf( stderr, "%s: Parse error in UI file\n", fileName ); + reader.setContentHandler( 0 ); + reader.setErrorHandler( 0 ); + delete hand; + f.close(); +} diff --git a/tools/linguist/lupdate/lupdate.pro b/tools/linguist/lupdate/lupdate.pro new file mode 100644 index 000000000..1dad999c3 --- /dev/null +++ b/tools/linguist/lupdate/lupdate.pro @@ -0,0 +1,21 @@ +TEMPLATE = app +CONFIG += qt warn_on console +HEADERS = ../shared/metatranslator.h \ + ../shared/proparser.h +SOURCES = fetchtr.cpp \ + main.cpp \ + merge.cpp \ + numberh.cpp \ + sametexth.cpp \ + ../shared/metatranslator.cpp \ + ../shared/proparser.cpp + +DEFINES += QT_INTERNAL_XML +include( ../../../src/qt_professional.pri ) + +TARGET = lupdate +INCLUDEPATH += ../shared +DESTDIR = ../../../bin + +target.path=$$bins.path +INSTALLS += target diff --git a/tools/linguist/lupdate/main.cpp b/tools/linguist/lupdate/main.cpp new file mode 100644 index 000000000..beb0624ce --- /dev/null +++ b/tools/linguist/lupdate/main.cpp @@ -0,0 +1,241 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include +#include + +#include +#include +#include +#include +#include +#include + +#include +#include + +// defined in fetchtr.cpp +extern void fetchtr_cpp( const char *fileName, MetaTranslator *tor, + const char *defaultContext, bool mustExist ); +extern void fetchtr_ui( const char *fileName, MetaTranslator *tor, + const char *defaultContext, bool mustExist ); + +// defined in merge.cpp +extern void merge( MetaTranslator *tor, const MetaTranslator *virginTor, + bool verbose ); + +typedef TQValueList TML; + +static void printUsage() +{ + fprintf( stderr, "Usage:\n" + " lupdate [options] project-file\n" + " lupdate [options] source-files -ts ts-files\n" + "Options:\n" + " -help Display this information and exit\n" + " -noobsolete\n" + " Drop all obsolete strings\n" + " -verbose\n" + " Explain what is being done\n" + " -version\n" + " Display the version of lupdate and exit\n" ); +} + +static void updateTsFiles( const MetaTranslator& fetchedTor, + const TQStringList& tsFileNames, const TQString& codec, + bool noObsolete, bool verbose ) +{ + TQStringList::ConstIterator t = tsFileNames.begin(); + while ( t != tsFileNames.end() ) { + MetaTranslator tor; + tor.load( *t ); + if ( !codec.isEmpty() ) + tor.setCodec( codec ); + if ( verbose ) + fprintf( stderr, "Updating '%s'...\n", (*t).latin1() ); + merge( &tor, &fetchedTor, verbose ); + if ( noObsolete ) + tor.stripObsoleteMessages(); + tor.stripEmptyContexts(); + if ( !tor.save(*t) ) + fprintf( stderr, "lupdate error: Cannot save '%s': %s\n", + (*t).latin1(), strerror(errno) ); + ++t; + } +} + +int main( int argc, char **argv ) +{ + TQString defaultContext = "@default"; + MetaTranslator fetchedTor; + TQCString codec; + TQStringList tsFileNames; + + bool verbose = FALSE; + bool noObsolete = FALSE; + bool metSomething = FALSE; + int numFiles = 0; + bool standardSyntax = TRUE; + bool metTsFlag = FALSE; + + int i; + + for ( i = 1; i < argc; i++ ) { + if ( qstrcmp(argv[i], "-ts") == 0 ) + standardSyntax = FALSE; + } + + for ( i = 1; i < argc; i++ ) { + if ( qstrcmp(argv[i], "-help") == 0 ) { + printUsage(); + return 0; + } else if ( qstrcmp(argv[i], "-noobsolete") == 0 ) { + noObsolete = TRUE; + continue; + } else if ( qstrcmp(argv[i], "-verbose") == 0 ) { + verbose = TRUE; + continue; + } else if ( qstrcmp(argv[i], "-version") == 0 ) { + fprintf( stderr, "lupdate version %s\n", QT_VERSION_STR ); + return 0; + } else if ( qstrcmp(argv[i], "-ts") == 0 ) { + metTsFlag = TRUE; + continue; + } + + numFiles++; + + TQString fullText; + + if ( !metTsFlag ) { + TQFile f( argv[i] ); + if ( !f.open(IO_ReadOnly) ) { + fprintf( stderr, "lupdate error: Cannot open file '%s': %s\n", + argv[i], strerror(errno) ); + return 1; + } + + TQTextStream t( &f ); + fullText = t.read(); + f.close(); + } + + TQString oldDir = TQDir::currentDirPath(); + TQDir::setCurrent( TQFileInfo(argv[i]).dirPath() ); + + if ( standardSyntax ) { + fetchedTor = MetaTranslator(); + codec.truncate( 0 ); + tsFileNames.clear(); + + TQMap tagMap = proFileTagMap( fullText ); + TQMap::Iterator it; + + for ( it = tagMap.begin(); it != tagMap.end(); ++it ) { + TQStringList toks = TQStringList::split( ' ', it.data() ); + TQStringList::Iterator t; + + for ( t = toks.begin(); t != toks.end(); ++t ) { + if ( it.key() == "HEADERS" || it.key() == "SOURCES" ) { + fetchtr_cpp( *t, &fetchedTor, defaultContext, TRUE ); + metSomething = TRUE; + } else if ( it.key() == "INTERFACES" || + it.key() == "FORMS" ) { + fetchtr_ui( *t, &fetchedTor, defaultContext, TRUE ); + fetchtr_cpp( *t + ".h", &fetchedTor, defaultContext, + FALSE ); + metSomething = TRUE; + } else if ( it.key() == "TRANSLATIONS" ) { + tsFileNames.append( *t ); + metSomething = TRUE; + } else if ( it.key() == "CODEC" || + it.key() == "DEFAULTCODEC" ) { + codec = (*t).latin1(); + } + } + } + + updateTsFiles( fetchedTor, tsFileNames, codec, noObsolete, + verbose ); + + if ( !metSomething ) { + fprintf( stderr, + "lupdate warning: File '%s' does not look like a" + " project file\n", + argv[i] ); + } else if ( tsFileNames.isEmpty() ) { + fprintf( stderr, + "lupdate warning: Met no 'TRANSLATIONS' entry in" + " project file '%s'\n", + argv[i] ); + } + } else { + if ( metTsFlag ) { + if ( TQString(argv[i]).lower().endsWith(".ts") ) { + TQFileInfo fi( argv[i] ); + if ( !fi.exists() || fi.isWritable() ) { + tsFileNames.append( argv[i] ); + } else { + fprintf( stderr, + "lupdate warning: For some reason, I cannot" + " save '%s'\n", + argv[i] ); + } + } else { + fprintf( stderr, + "lupdate error: File '%s' lacks .ts extension\n", + argv[i] ); + } + } else { + TQFileInfo fi(argv[i]); + if ( TQString(argv[i]).lower().endsWith(".ui") ) { + fetchtr_ui( fi.fileName(), &fetchedTor, defaultContext, TRUE ); + fetchtr_cpp( TQString(fi.fileName()) + ".h", &fetchedTor, + defaultContext, FALSE ); + } else { + fetchtr_cpp( fi.fileName(), &fetchedTor, defaultContext, TRUE ); + } + } + } + TQDir::setCurrent( oldDir ); + } + + if ( !standardSyntax ) + updateTsFiles( fetchedTor, tsFileNames, codec, noObsolete, verbose ); + + if ( numFiles == 0 ) { + printUsage(); + return 1; + } + return 0; +} diff --git a/tools/linguist/lupdate/merge.cpp b/tools/linguist/lupdate/merge.cpp new file mode 100644 index 000000000..47720b1b8 --- /dev/null +++ b/tools/linguist/lupdate/merge.cpp @@ -0,0 +1,129 @@ +/********************************************************************** +** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include + +// defined in numberh.cpp +extern void applyNumberHeuristic( MetaTranslator *tor, bool verbose ); +// defined in sametexth.cpp +extern void applySameTextHeuristic( MetaTranslator *tor, bool verbose ); + +typedef TQValueList TML; + +/* + Merges two MetaTranslator objects into the first one. The first one + is a set of source texts and translations for a previous version of + the internationalized program; the second one is a set of fresh + source texts newly extracted from the source code, without any + translation yet. +*/ + +void merge( MetaTranslator *tor, const MetaTranslator *virginTor, bool verbose ) +{ + int known = 0; + int neww = 0; + int obsoleted = 0; + TML all = tor->messages(); + TML::Iterator it; + + /* + The types of all the messages from the vernacular translator + are updated according to the virgin translator. + */ + for ( it = all.begin(); it != all.end(); ++it ) { + MetaTranslatorMessage::Type newType; + MetaTranslatorMessage m = *it; + + // skip context comment + if ( !TQCString((*it).sourceText()).isEmpty() ) { + if ( !virginTor->contains((*it).context(), (*it).sourceText(), + (*it).comment()) ) { + newType = MetaTranslatorMessage::Obsolete; + if ( m.type() != MetaTranslatorMessage::Obsolete ) + obsoleted++; + } else { + switch ( m.type() ) { + case MetaTranslatorMessage::Finished: + newType = MetaTranslatorMessage::Finished; + known++; + break; + case MetaTranslatorMessage::Unfinished: + default: + newType = MetaTranslatorMessage::Unfinished; + known++; + break; + case MetaTranslatorMessage::Obsolete: + newType = MetaTranslatorMessage::Unfinished; + neww++; + } + } + + if ( newType != m.type() ) { + m.setType( newType ); + tor->insert( m ); + } + } + } + + /* + Messages found only in the virgin translator are added to the + vernacular translator. Among these are all the context comments. + */ + all = virginTor->messages(); + + for ( it = all.begin(); it != all.end(); ++it ) { + if ( !tor->contains((*it).context(), (*it).sourceText(), + (*it).comment()) ) { + tor->insert( *it ); + if ( !TQCString((*it).sourceText()).isEmpty() ) + neww++; + } + } + + /* + The same-text heuristic handles cases where a message has an + obsolete counterpart with a different context or comment. + */ + applySameTextHeuristic( tor, verbose ); + + /* + The number heuristic handles cases where a message has an + obsolete counterpart with mostly numbers differing in the + source text. + */ + applyNumberHeuristic( tor, verbose ); + + if ( verbose ) + fprintf( stderr, " %d known, %d new and %d obsoleted messages\n", known, + neww, obsoleted ); +} diff --git a/tools/linguist/lupdate/numberh.cpp b/tools/linguist/lupdate/numberh.cpp new file mode 100644 index 000000000..787c9a4e1 --- /dev/null +++ b/tools/linguist/lupdate/numberh.cpp @@ -0,0 +1,248 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include + +#include +#include +#include +#include + +#include + +typedef TQMap TMM; +typedef TQValueList TML; + +static bool isDigitFriendly( int c ) +{ + return ispunct((uchar)c) || isspace((uchar)c); +} + +static int numberLength( const char *s ) +{ + int i = 0; + + if ( isdigit((uchar)s[0]) ) { + do { + i++; + } while (isdigit((uchar)s[i]) || + (isDigitFriendly(s[i]) && + (isdigit((uchar)s[i + 1]) || + (isDigitFriendly(s[i + 1]) && isdigit((uchar)s[i + 2]))))); + } + return i; +} + +/* + Returns a version of 'key' where all numbers have been replaced by zeroes. If + there were none, returns "". +*/ +static TQCString zeroKey( const char *key ) +{ + TQCString zeroed( (int)strlen(key) + 1 ); + char *z = zeroed.data(); + int i = 0, j = 0; + int len; + bool metSomething = FALSE; + + while ( key[i] != '\0' ) { + len = numberLength( key + i ); + if ( len > 0 ) { + i += len; + z[j++] = '0'; + metSomething = TRUE; + } else { + z[j++] = key[i++]; + } + } + z[j] = '\0'; + + if ( metSomething ) + return zeroed; + else + return ""; +} + +static TQString translationAttempt( const TQString& oldTranslation, + const char *oldSource, + const char *newSource ) +{ + int p = zeroKey( oldSource ).contains( '0' ); + int oldSourceLen = qstrlen( oldSource ); + TQString attempt; + TQStringList oldNumbers; + TQStringList newNumbers; + TQMemArray met( p ); + TQMemArray matchedYet( p ); + int i, j; + int k = 0, ell, best; + int m, n; + int pass; + + /* + This algorithm is hard to follow, so we'll consider an example + all along: oldTranslation is "XeT 3.0", oldSource is "TeX 3.0" + and newSource is "XeT 3.1". + + First, we set up two tables: oldNumbers and newNumbers. In our + example, oldNumber[0] is "3.0" and newNumber[0] is "3.1". + */ + for ( i = 0, j = 0; i < oldSourceLen; i++, j++ ) { + m = numberLength( oldSource + i ); + n = numberLength( newSource + j ); + if ( m > 0 ) { + oldNumbers.append( TQCString(oldSource + i, m + 1) ); + newNumbers.append( TQCString(newSource + j, n + 1) ); + i += m; + j += n; + met[k] = FALSE; + matchedYet[k] = 0; + k++; + } + } + + /* + We now go over the old translation, "XeT 3.0", one letter at a + time, looking for numbers found in oldNumbers. Whenever such a + number is met, it is replaced with its newNumber equivalent. In + our example, the "3.0" of "XeT 3.0" becomes "3.1". + */ + for ( i = 0; i < (int) oldTranslation.length(); i++ ) { + attempt += oldTranslation[i]; + for ( k = 0; k < p; k++ ) { + if ( oldTranslation[i] == oldNumbers[k][matchedYet[k]] ) + matchedYet[k]++; + else + matchedYet[k] = 0; + } + + /* + Let's find out if the last character ended a match. We make + two passes over the data. In the first pass, we try to + match only numbers that weren't matched yet; if that fails, + the second pass does the trick. This is useful in some + suspicious cases, flagged below. + */ + for ( pass = 0; pass < 2; pass++ ) { + best = p; // an impossible value + for ( k = 0; k < p; k++ ) { + if ( (!met[k] || pass > 0) && + matchedYet[k] == (int) oldNumbers[k].length() && + numberLength(oldTranslation.latin1() + (i + 1) - + matchedYet[k]) == matchedYet[k] ) { + // the longer the better + if ( best == p || matchedYet[k] > matchedYet[best] ) + best = k; + } + } + if ( best != p ) { + attempt.truncate( attempt.length() - matchedYet[best] ); + attempt += newNumbers[best]; + met[best] = TRUE; + for ( k = 0; k < p; k++ ) + matchedYet[k] = 0; + break; + } + } + } + + /* + We flag two kinds of suspicious cases. They are identified as + such with comments such as "{2000?}" at the end. + + Example of the first kind: old source text "TeX 3.0" translated + as "XeT 2.0" is flagged "TeX 2.0 {3.0?}", no matter what the + new text is. + */ + for ( k = 0; k < p; k++ ) { + if ( !met[k] ) + attempt += TQString( " {" ) + newNumbers[k] + TQString( "?}" ); + } + + /* + Example of the second kind: "1 of 1" translated as "1 af 1", + with new source text "1 of 2", generates "1 af 2 {1 or 2?}" + because it's not clear which of "1 af 2" and "2 af 1" is right. + */ + for ( k = 0; k < p; k++ ) { + for ( ell = 0; ell < p; ell++ ) { + if ( k != ell && oldNumbers[k] == oldNumbers[ell] && + newNumbers[k] < newNumbers[ell] ) + attempt += TQString( " {" ) + newNumbers[k] + TQString( " or " ) + + newNumbers[ell] + TQString( "?}" ); + } + } + return attempt; +} + +/* + Augments a MetaTranslator with translations easily derived from + similar existing (probably obsolete) translations. + + For example, if "TeX 3.0" is translated as "XeT 3.0" and "TeX 3.1" + has no translation, "XeT 3.1" is added to the translator and is + marked Unfinished. +*/ +void applyNumberHeuristic( MetaTranslator *tor, bool verbose ) +{ + TMM translated, untranslated; + TMM::Iterator t, u; + TML all = tor->messages(); + TML::Iterator it; + int inserted = 0; + + for ( it = all.begin(); it != all.end(); ++it ) { + if ( (*it).type() == MetaTranslatorMessage::Unfinished ) { + if ( (*it).translation().isEmpty() ) + untranslated.insert(TQCString((*it).context()) + "\n" + (*it).sourceText() + "\n" + + (*it).comment(), *it); + } else if ( !(*it).translation().isEmpty() ) { + translated.insert( zeroKey((*it).sourceText()), *it ); + } + } + + for ( u = untranslated.begin(); u != untranslated.end(); ++u ) { + t = translated.find( zeroKey((*u).sourceText()) ); + if ( t != translated.end() && !t.key().isEmpty() && + qstrcmp((*t).sourceText(), (*u).sourceText()) != 0 ) { + MetaTranslatorMessage m( *u ); + m.setTranslation(translationAttempt((*t).translation(), (*t).sourceText(), + (*u).sourceText())); + tor->insert( m ); + inserted++; + } + } + if ( verbose && inserted != 0 ) + fprintf( stderr, " number heuristic provided %d translation%s\n", + inserted, inserted == 1 ? "" : "s" ); +} diff --git a/tools/linguist/lupdate/sametexth.cpp b/tools/linguist/lupdate/sametexth.cpp new file mode 100644 index 000000000..6db1a80c4 --- /dev/null +++ b/tools/linguist/lupdate/sametexth.cpp @@ -0,0 +1,97 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include + +#include +#include + +typedef TQMap TMM; +typedef TQValueList TML; + +/* + Augments a MetaTranslator with trivially derived translations. + + For example, if "Enabled:" is consistendly translated as "Eingeschaltet:" no + matter the context or the comment, "Eingeschaltet:" is added as the + translation of any untranslated "Enabled:" text and is marked Unfinished. +*/ + +void applySameTextHeuristic( MetaTranslator *tor, bool verbose ) +{ + TMM translated; + TMM avoid; + TMM::Iterator t; + TML untranslated; + TML::Iterator u; + TML all = tor->messages(); + TML::Iterator it; + int inserted = 0; + + for ( it = all.begin(); it != all.end(); ++it ) { + if ( (*it).type() == MetaTranslatorMessage::Unfinished ) { + if ( (*it).translation().isEmpty() ) + untranslated.append( *it ); + } else { + TQCString key = (*it).sourceText(); + t = translated.find( key ); + if ( t != translated.end() ) { + /* + The same source text is translated at least two + different ways. Do nothing then. + */ + if ( (*t).translation() != (*it).translation() ) { + translated.remove( key ); + avoid.insert( key, *it ); + } + } else if ( !avoid.contains(key) && + !(*it).translation().isEmpty() ) { + translated.insert( key, *it ); + } + } + } + + for ( u = untranslated.begin(); u != untranslated.end(); ++u ) { + TQCString key = (*u).sourceText(); + t = translated.find( key ); + if ( t != translated.end() ) { + MetaTranslatorMessage m( *u ); + m.setTranslation( (*t).translation() ); + tor->insert( m ); + inserted++; + } + } + if ( verbose && inserted != 0 ) + fprintf( stderr, " same-text heuristic provided %d translation%s\n", + inserted, inserted == 1 ? "" : "s" ); +} diff --git a/tools/linguist/phrasebooks/danish.qph b/tools/linguist/phrasebooks/danish.qph new file mode 100644 index 000000000..c4926bd7e --- /dev/null +++ b/tools/linguist/phrasebooks/danish.qph @@ -0,0 +1,1018 @@ + + + About + Om + + + access key + hurtigtast + + + accessibility + brugervenlighed + + + action handle + genvejshåndtag + + + active + aktiv + + + active end + markeringsafslutning + + + active object + aktivt objekt + + + active window + aktivt vindue + + + adornment + værktøjselement + + + Always on Top + Altid øverst + + + anchor point + forankringspunkt + + + Apply + Anvend + + + auto-exit + tekstboks med automatisk udgang + + + auto-repeat + automatisk gentagelse + + + automatic link + automatisk kæde + + + automatic scrolling + automatisk rulning + + + autoscroll + automatisk rulning + + + Back + Tilbage + + + Browse + Gennemse + + + Cancel + Annuller + + + cascading menu + undermenu + + + check box + afkrydsningsfelt + + + check mark + afkrydsning + + + child window + underordnet vindue + + + choose + vælge + + + click + klikke + + + Clipboard + Udklipsholder + + + Close + Luk + + + Close button + lukknap + + + collapse + skjule + outline/disposition + + + column heading + kolonneoverskrift + control/kontrolelement + + + combo box + kombinationsboks + + + command button + kommandoknap + + + container + objektbeholder + + + context-sensitive Help + kontekstafhængig hjælp + + + contextual + kontekstafhængig + + + control + kontrolelement + + + Copy + Kopier + + + Copy here + Kopier hertil + + + Create Shortcut + Opret genvej + + + Create Shortcut Here + Opret genvej her + + + Cut + Klip + + + default + standard + + + default button + standardknap + + + Delete + Slet + + + desktop + skrivebord + + + destination + destination + + + dialog box + dialogboks + + + disability + handicap + + + disjoint selection + usammenhængende markering + + + dock + forankre + + + document + dokument + + + double-click + dobbeltklikke + + + drag + trække + + + drag-and-drop + trække og slippe + + + drop-down combo box + kombinationsboks med rullepil + + + drop-down list box + rulleliste + + + drop-down menu + rullemenu + + + Edit + Rediger + + + Edit menu + Menuen Rediger + + + ellipsis + ellipse + + + embedded object + integreret objekt + + + Exit + Afslut + + + expand + udvide + an outline/en disposition + + + Explore + Stifinder + + + extended selection + udvidet markering + + + extended selection list box + liste + der tillader udvidet markering + + + file + fil + + + File menu + Menuen Filer + + + Find + Søg + + + Find Next + Find næste + + + Find What + Søg efter + + + folder + mappe + + + font + skrifttype + + + font size + skriftstørrelse + + + font style + typografi + + + function key + funktionstast + + + group box + gruppeboks + + + handle + håndtag + + + Help + Hjælp + + + Help menu + Menuen Hjælp + + + Hide + Skjul + + + hierarchical selection + hierarkisk markering + + + hold + holde nede + + + hot spot + aktivt punkt + + + hot zone + aktiv zone + + + icon + ikon + + + inactive + ikke-aktiv + + + inactive window + ikke-aktivt vindue + + + input focus + inputfokus + + + Insert + Menuen Indsæt + + + Insert Object + Indsæt objekt + + + insertion point + indsætningspunkt + + + italic + kursiv + + + label + etiket + + + landscape + liggende + + + link + sammenkæde + verb + + + link + kæde + noun + + + Link Here + Indsæt kæde her + + + list box + liste + + + list view + listevisningsboks + control/kontrolelement + + + manual link + manuel kæde + + + Maximize + Maksimer + + + maximize button + maksimeringsknap + + + MDI + MDI + + + menu + menu + + + menu bar + menulinje + + + menu button + menuknap + + + menu item + menupunkt + + + menu title + menutitel + + + message box + meddelelsesboks + + + Minimize + Minimer + + + minimize button + minimeringsknap + + + mixed-value + blandet værdi + + + modal + modal + + + mode + tilstand + + + modeless + ikke-modal + + + modifier key + ændringstast + + + mouse + mus + + + Move + Flyt + + + Move Here + Flyt hertil + + + Multiple Document Interface + multiple document interface + MDI + + + multiple selection list box + liste + der tillader flere markeringer + + + My Computer + Denne computer + icon/ikon + + + Network Neighborhood + Andre computere + icon/ikon + + + New + Ny + + + Next + Næste + + + object + objekt + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + OLE-træk og slip + + + OLE embedded object + integreret OLE-objekt + + + OLE linked object + sammenkædet OLE-objekt + + + OLE nondefault drag and drop + interaktiv OLE-træk og slip + + + Open + Åbn + + + Open With + Åbn med + + + option button + alternativknap + + + option-set + aktiveret indstilling + + + package + objektpakke + + + Page Setup + Sideopsætning + + + palette window + paletvindue + + + pane + rude + + + parent window + overordnet vindue + + + password + adgangskode + + + Paste + Sæt ind + + + Paste Link + Indsæt kæde + + + Paste Shortcut + Indsæt genvej + + + Paste Special + Indsæt speciel + + + path + sti + + + Pause + Pause + + + Play + Afspil + + + Plug and Play + Plug and Play + + + point + punkt + noun + + + point + pege + verb + + + pointer + markør + + + pop-up menu + pop-up-menu + + + pop-up window + pop-up-vindue + + + portrait + stående + + + press + trykke på + and hold a mouse button/og holde en museknap nede + + + press + trykke på + a key/en tast + + + primary container + primært destinationsobjekt + + + primary window + primært vindue + + + Print + Udskriv + + + printer + printer + + + progress indicator + statusindikator + control/kontrolelement + + + project + projekt + + + Properties + Egenskaber + + + property inspector + egenskabsfremviser + + + property page + egenskabsside + + + property sheet + egenskabsark + + + property sheet control + kontrolelement på egenskabsark + + + Quick View + Hurtig visning + + + read-only + skrivebeskyttet + + + Recycle Bin + Papirkurv + Icon/ikon + + + Redo + Annuller Fortryd + + + region selection + områdemarkering + + + registry + registreringsdatabase + + + Repeat + Gentag + + + Replace + Erstat + + + Restore + Gendan + + + Restore button + gendannelsesknap + + + Resume + Fortsæt + + + Retry + Forsøg igen + + + rich-text box + tekstboks til formateret tekst + + + Run + Kør + + + Save + Gem + + + Save as + Gem som + + + scroll + rulle + + + scroll arrow + rullepil + + + scroll bar + rullepanel + + + scroll box + rulleboks + + + secondary window + sekundært vindue + + + select + markere + + + select + vælge + + + Select All + Marker alt + + + selection + det markerede + + + selection handle + markeringshåndtag + + + Send To + Overfør til + + + separator + separator + + + Settings + Indstillinger + + + Setup + Indstillinger + + + Setup + Installation + + + shortcut + genvej + + + shortcut button + genvejsknap + + + shortcut icon + genvejsikon + + + shortcut key + genvejstast + + + shortcut key control + kontrolelement til genvejstast + + + Show + Vis + + + Shutdown + Luk computeren + + + single selection list box + liste + der kun tillader en enkelt markering + + + Size + Tilpas størrelse + + + size grip + størrelseshåndtag + + + slider + skala + + + spin box + rotationsboks + + + Split + Opdel + + + split bar + delelinje + + + split box + deleboks + + + Start button + startknap + + + StartUp folder + Startmappe + + + status bar + statuslinje + + + Stop + Stop + + + tab control + fane + + + task bar + proceslinje + + + task-oriented Help + opgaveafhængig Hjælp + + + template + skabelon + + + text box + tekstboks + + + title bar + titellinje + + + title text + titeltekst + + + toggle key + til/fra-tast + + + toolbar + verktøjslinje + + + tooltip + verktøjstip + + + tree view control + træstruktur + + + type + skrive + verb + + + type + type + noun + + + unavailable + ikke tilgængelig + + + Undo + Fortryd + + + Uninstall + Fjern installationen + + + View + Menuen Vis + + + visual editing + lokal redigering + + + well control + grafikpalet + + + What's This? + Hvad er det? + + + Window + Menuen Vindue + + + window + vindue + + + Windows Explorer + Windows Stifinder + + + wizard + guide + + + workbook + projektmappe + + + workgroup + arbejdsgruppe + + + workspace + arbejdsområde + + + Yes + Ja + + diff --git a/tools/linguist/phrasebooks/dutch.qph b/tools/linguist/phrasebooks/dutch.qph new file mode 100644 index 000000000..0e9b5d689 --- /dev/null +++ b/tools/linguist/phrasebooks/dutch.qph @@ -0,0 +1,1044 @@ + + + About + Info + + + access key + toegangstoets + + + accessibility + toegankelijkheid + + + action handle + bewerkingsgreep + + + active + actief + + + active end + selecie-einde + + + active object + actief object + + + active window + actief venster + + + adornment + grafisch hulpmiddel + + + Always on Top + Altijd op voorgrond + + + anchor point + fixeerpunt + + + Apply + Toepassen + + + auto-exit + automatisch verlaten + + + auto-repeat + zich automatisch herhalen + + + auto-repeat + automatisch herhalen + + + automatic link + automatische koppeling + + + automatic scrolling + automatisch schuiven + + + autoscroll + automatisch schuiven + + + Back + Vorige + wanneer het een logisch paar vormt met Volgende + + + Browse + Bladeren + + + Cancel + Annuleren + + + cascading menu + vervolgmenu + + + check box + selectievakje + + + check mark + vinkje + + + child window + subvenster + + + choose + kiezen + + + click + klikken + + + Clipboard + Klembord + + + Close + Sluiten + + + Close button + knop Sluiten + + + collapse + samenvouwen + outline + + + column heading + kolomnaam + control + + + combo box + keuzelijst met invoervak + + + command button + opdrachtknop + + + container + hoofdobject + + + context-sensitive Help + contextafhankelijke Help + + + contextual + contextafhankelijk + + + control + besturingselement + + + Copy + Kopiëren + + + Copy here + Hierheen kopiëren + + + Create Shortcut + Snelkoppeling maken + + + Create Shortcut Here + Hier snelkoppeling maken + + + Cut + Knippen + + + default + standaard + + + default button + standaardknop + + + Delete + Verwijderen + + + desktop + bureaublad + + + destination + doel + + + dialog box + dialoogvenster + + + disability + handicap + voorzichtig in context, maar handicap niet verbloemen:VB: persoon met een handicap (beter dan gehandicapte) + + + disjoint selection + niet-aaneengesloten selectie + + + dock + in werkbalkdok plaatsen + + + document + document + + + double-click + dubbelklikken + + + drag + slepen + + + drag-and-drop + slepen en neerzetten + + + drop-down combo box + vervolgkeuzelijst met invoervak + + + drop-down list box + vervolgkeuzelijst + + + drop-down menu + menu + + + Edit + Bewerken + + + Edit menu + menu Bewerken + + + ellipsis + puntjes + (...) + + + embedded object + ingesloten object + + + Exit + Afsluiten + + + expand + uitvouwen + an outline + + + Explore + Verkennen + + + extended selection + uitgebreide selectie + + + extended selection list box + keuzelijst met uitgebreide selectie + + + file + bestand + + + File menu + menu Bestand + + + Find + Zoeken + + + Find Next + Volgende zoeken + + + Find What + Zoeken naar + + + folder + map + + + font + lettertype + + + font size + tekengrootte + + + font style + tekenstijl + + + function key + functietoets + + + group box + groepsvak + + + handle + greep + + + Help + Help + + + Help menu + menu Help + + + Hide + Verbergen + + + hierarchical selection + hiërarchische selectie + + + hold + ingedrukt houden + + + hot spot + selectiepunt + + + hot zone + selectiegebied + + + icon + pictogram + + + inactive + niet-actief + + + inactive window + niet-actief venster + + + input focus + invoerfocus + + + Insert + menu Invoegen + + + Insert Object + Object Invoegen + + + insertion point + invoegpositie + + + italic + cursief + + + label + label + gender, Masc.: de + + + landscape + liggend + + + link + koppeling + noun + + + link + koppelen + verb + + + Link Here + Hier koppeling maken + + + list box + keuzelijst + + + list view + weergaveknoppen + control + + + manual link + handmatige koppeling + + + Maximize + Maximaliseren + + + maximize button + knop Maximaliseren + + + MDI + MDI + + + menu + menu + + + menu bar + menubalk + + + menu button + menuknop + + + menu item + opdracht + + + menu title + menunaam + + + message box + berichtvak + + + Minimize + Minimaliseren + + + minimize button + knop Minimaliseren + + + mixed-value + met gemengde waarden + + + modal + modusgebonden + + + mode + modi + plural + + + mode + modus + singular + + + modeless + niet-modusgebonden + + + modifier key + modificatietoets + + + mouse + muis + + + Move + Verplaatsen + + + Move Here + Hierheen verplaatsen + + + Multiple Document Interface + interface voor meerdere documenten + + + multiple selection list box + keuzelijst met meervoudige selectie + + + My Computer + Deze computer + icon/pictogram + + + Network Neighborhood + Netwerkomgeving + icon/pictogram + + + New + Nieuw + + + Next + Volgende + + + object + object + + + OK + OK + + + OLE + OLE + OLE (objecten koppelen en insluiten): voluit alleen in doc en Help + + + OLE drag and drop + slepen en neerzetten + + + OLE drag and drop + slepen en neerzetten via OLE + + + OLE embedded object + ingesloten OLE-object + + + OLE linked object + gekoppeld OLE-object + + + OLE nondefault drag and drop + Aangepast slepen en neerzetten + + + OLE nondefault drag and drop + Aangepast slepen en neerzetten via OLE + + + Open + Openen + + + Open With + Openen met + + + option button + keuzerondje + + + option-set + opties + + + package + OLE-pakket + + + Page Setup + Pagina-instelling + + + palette window + paletvenster + + + pane + deelvenster + + + parent window + hoofdvenster + + + password + wachtwoord + + + Paste + Plakken + + + Paste Link + Koppeling plakken + + + Paste Shortcut + Snelkoppeling plakken + + + Paste Special + Plakken speciaal + + + path + pad + + + Pause + Pauze + + + Play + Afspelen + + + Plug and Play + Plug en Play + + + point + aanwijzen + + + pointer + aanwijzer + + + pop-up menu + pop-up-menu + + + pop-up window + pop-up-venster + + + portrait + staand + + + press + drukken op + a key/een toets + + + press + ingedrukt houden + and hold a mouse button/een muisknop + + + press + een muisknop ingedrukt houden + and hold a mouse button + + + press a mouse botton + een muisknop indrukken + + + primary container + primair hoofdobject + + + primary window + primair venster + + + Print + Afdrukken + + + printer + printer + + + progress indicator + voortgangsindicator + control + + + project + project + + + Properties + Eigenschappen + + + property inspector + eigenschappenweergave + + + property page + eigenschappenpagina + + + property sheet + eigenschappenblad + + + property sheet control + besturingselement op een eigenschappenblad + + + Quick View + Snel weergeven + + + read-only + alleen-lezen + + + Recycle Bin + Prullenbak + Icon/pictogram + + + Redo + Opnieuw + + + region selection + gebiedsselectie + + + registry + het Register + + + Repeat + Herhalen + + + Replace + Vervangen + + + Restore + Vorig formaat + + + Restore button + knop Vorig formaat + + + Resume + Doorgaan + + + Retry + Nogmaals + + + rich-text box + RTF-vak + + + Run + Uitvoeren + Maar: macro starten + + + Save + Opslaan + + + Save as + Opslaan als + + + scroll + schuiven door + + + scroll arrow + schuifpijl + + + scroll bar + schuifbalk + + + scroll box + schuifblok + + + secondary window + secundair venster + + + select + selecteren + + + Select All + Alles selecteren + + + selection + selectie + + + selection handle + selectiegreep + + + Send To + Kopiëren naar + + + separator + scheidingsteken + + + Settings + Instellingen + + + Setup + Instellen + + + Setup + Setup + als het programma Setup wordt bedoeld + + + shortcut + snelkoppeling + + + shortcut button + snelkoppelingsknop + + + shortcut icon + snelkoppelingspictogram + + + shortcut key + sneltoets + + + shortcut key control + sneltoetsvak + + + Show + Weergeven + + + Shutdown + Afsluiten + + + single selection list box + keuzelijst met enkelvoudige selectie + + + Size + Formaat wijzigen + + + size grip + formaatgreep + + + slider + schuifregelaar + + + spin box + kringveld + + + Split + Splitsen + + + split bar + splitsbalk + + + split box + splitsblokje + + + Start button + knop Start + + + StartUp folder + map Opstarten + + + status bar + statusbalk + + + Stop + Stoppen + + + tab control + tab + + + task bar + taakbalk + + + task-oriented Help + taakgeoriënteerde Help + + + template + sjabloon + de + + + text box + tekstvak + + + title bar + titelbalk + + + title text + venstertitel + + + toggle key + wisseltoets + + + toolbar + werkbalk + + + tooltip + knopinfo + + + tree view control + besturingselement voor structuurweergave + + + tree view control + structuurweergave + + + type + typen + verb + + + type + type + noun + + + unavailable + niet beschikbaar + + + Undo + Ongedaan maken + + + Uninstall + Installatie ongedaan maken + + + View + menu Beeld + + + visual editing + direct bewerken + + + well control + keuzelijst met grafische opties + + + What's This? + Wat is dit? + + + Window + menu Venster + + + window + venster + + + Windows Explorer + Windows Verkenner + + + wizard + wizard + geen hoofdletter meer in lopende tekst + + + workbook + werkmap + + + workgroup + werkgroep + + + workspace + werkruimte + + + Yes + Ja + + diff --git a/tools/linguist/phrasebooks/finnish.qph b/tools/linguist/phrasebooks/finnish.qph new file mode 100644 index 000000000..0612c8275 --- /dev/null +++ b/tools/linguist/phrasebooks/finnish.qph @@ -0,0 +1,1033 @@ + + + About + Tietoja + + + access key + valintanäppäin + + + accessibility + helppokäyttötoiminto + + + action handle + toimintokahva + + + active + aktiivinen + + + active end + valinnan aktiivinen päätöskohta + + + active object + aktiivinen objekti + + + active window + aktiivinen ikkuna + + + adornment + graafinen lisäke + + + Always on Top + Aina päällimmäisenä + + + anchor point + ankkurikohta + + + Apply + Käytä + + + auto-exit + automaattinen siirtyminen + + + auto-repeat + automaattinen toisto + + + automatic link + automaattinen linkki + + + automatic scrolling + automaattinen vieritys + + + autoscroll + automaattinen vieritys + + + Back + Takaisin + + + Browse + Selaa + + + Cancel + Peruuta + + + cascading menu + alivalikko + + + check box + valintaruutu + + + check mark + valintamerkki + + + child window + ali-ikkuna + + + choose + valita + + + click + napsautta + + + Clipboard + Leikepöytä + + + Close + Sulje + + + Close button + sulkemispainike + + + collapse + tiivistää + outline/jäsennys + + + collapse + kutistaa + outline/jäsennys + + + column heading + saraketunnus + control/ohjausobjekti + + + column heading + sarakeotsikko + control/ohjausobjekti + + + combo box + yhdistelmäruutu + + + command button + painike + + + command button + komento painike + + + container + säilö + + + context-sensitive Help + tilannekohtainen ohje + + + contextual + tilannekohtainen + + + control + ohjausobjekti + + + Copy + Kopioi + + + Copy here + Kopioi tähän + + + Create Shortcut + Luo pikakuvake + + + Create Shortcut Here + Luo pikakuvake tähän + + + Cut + Leikkaa + + + default + oletus + + + default button + oletuspainike + + + Delete + Poista + + + desktop + työpöytä + + + destination + kohde + + + dialog box + valintaikkuna + + + disability + invaliditeetti + + + disjoint selection + hajavalinta + + + dock + telakoida + + + document + tiedosto + + + document + asiakirja + + + double-click + kaksoisnapsauttaa + + + drag + vetää + + + drag-and-drop + vetää ja pudottaa + + + drop-down combo box + avattava yhdistelmäruutu + + + drop-down list box + avattava luetteloruutu + + + drop-down menu + avattava valikko + + + Edit + Muokkaa + + + Edit menu + Muokkaa-valikko + + + ellipsis + kolme pistettä + + + embedded object + upotettu objekti + + + Exit + Lopeta + + + expand + laajentaa + an outline/jäsennys + + + Explore + Selaa + + + extended selection + laajennettu valinta + + + extended selection list box + laajennettu valinta-luetteloruutu + + + file + tiedosto + + + File menu + Tiedosto-valikko + + + Find + Etsi + + + Find Next + Etsi seuraava + + + Find What + Etsittävä + + + folder + kansio + + + font + fontti + + + font size + fonttikoko + + + font style + fonttityyli + + + function key + funktionäppäin + + + group box + ryhmän kehys + + + handle + kahva + + + Help + Ohje + + + Help menu + Ohje-valikko + + + Hide + Piilota + + + hierarchical selection + hierarkkinen valinta + + + hold + pitää painettuna + + + hot spot + kohdepiste + + + hot zone + kohdealue + + + icon + kuvake + + + inactive + passiivinen + + + inactive window + passiivinen ikkuna + + + input focus + syöttöalue + + + Insert + Lisää-valikko + + + Insert Object + Lisää objekti + + + insertion point + lisäyskohta + + + italic + kursivoitu + + + label + otsikko + + + label + nimi + + + landscape + vaaka + + + link + linkki + noun + + + link + linkittää + verb + + + Link Here + Linkitä tähän + + + list box + luetteloruutu + + + list view + luettelonäyttö + control/ohjausobjekti + + + manual link + manuaalinen linkki + + + Maximize + Suurenna + + + maximize button + suurennuspainike + + + MDI + MDI + + + menu + valikko + + + menu bar + valikkorivi + + + menu button + valikkopainike + + + menu item + valikon vaihtoehto + + + menu title + valikon otsikko + + + message box + sanomaruutu + + + Minimize + Pienennä + + + minimize button + pienennyspainike + + + mixed-value + monitila + + + modal + modaalinen + + + mode + tila + + + modeless + ei-modaalinen + + + modifier key + yhdistelmänäppäin + + + mouse + hiiri + + + Move + Siirrä + + + Move Here + Siirrä tähän + + + Multiple Document Interface + MDI-liittymä + + + multiple selection list box + monivalintainen luetteloruutu + + + My Computer + Oma tietokone + icon/kuvake + + + Network Neighborhood + Verkkoympäristö + icon/kuvake + + + New + Uusi + + + Next + Seuraava + + + object + objekti + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + vedä ja pudota-OLE-toiminto + + + OLE embedded object + upotettu OLE-objekti + + + OLE linked object + linkitetty OLE-objekti + + + OLE nondefault drag and drop + käyttäjän määrittämä vedä ja pudota-OLE-toiminto + + + Open + Avaa + + + Open With + Avaa sovelluksessa + + + option button + valintanappi + + + option-set + valitsimen tila + + + package + pakkaus + + + Page Setup + Sivun asetukset + + + palette window + valikoimaikkuna + + + pane + ruutu + + + parent window + ylemmän tason ikkuna + + + password + salasana + + + Paste + Liitä + + + Paste Link + Liitä linkki + + + Paste Shortcut + Liitä pikakuvake + + + Paste Special + Liitä määräten + + + path + polku + + + Pause + Tauko + + + Play + Soita + + + Plug and Play + Plug and Play + + + point + piste + + + point + osoittaa + + + pointer + osoitin + + + pop-up menu + pikavalikko + + + pop-up window + ponnahdusikkuna + + + portrait + pysty + + + press + painaa + and hold a mouse button/ja pitää painettuna hiiripainiketta + + + press + painaa + a key/näppäintä + + + primary container + ensisijainen säilö + + + primary window + ensisijainen ikkuna + + + Print + Tulosta + + + printer + kirjoitin + + + progress indicator + tilanneilmaisin + control/ohjausobjekti + + + project + projekti + + + Properties + Ominaisuudet + + + property inspector + ominaisuuksien tarkastelu + + + property page + ominaisuusryhmä + + + property sheet + ominaisuusikkuna + + + property sheet control + ominaisuusikkuna-ohjausobjekti + + + Quick View + Pikanäyttö + + + read-only + vain luku + + + Recycle Bin + Roskakori + Icon/kuvake + + + Redo + Tee uudelleen + + + region selection + aluevalinta + + + registry + rekisteri + + + Repeat + Toista + + + Replace + Korvaa + + + Restore + Palauta + + + Restore button + palautuspainike + + + Resume + Jatka + + + Retry + Yritä uudelleen + + + rich-text box + monimuotoruutu + + + Run + Suorita + + + Save + Tallenna + + + Save as + Tallenna nimellä + + + scroll + vierittää + + + scroll arrow + vieritysnuoli + + + scroll bar + vierityspalkki + + + scroll box + vieritysruutu + + + secondary window + toissijainen ikkuna + + + select + valita + + + Select All + Valitse kaikki + + + selection + valinta + + + selection handle + valintakahva + + + Send To + Lähetä tiedosto + + + separator + erotin + + + Settings + Asetukset + + + Setup + Asennus + + + shortcut + pika- + + + shortcut button + pikapainike + + + shortcut icon + pikakuvake + + + shortcut key + pikanäppäin + + + shortcut key control + pikanäppäin-ohjausobjekti + + + Show + Näytä + + + Shutdown + Sammuta + + + single selection list box + yksivalintainen luetteloruutu + + + Size + Muuta kokoa + + + size grip + koonmuuttokahva + + + slider + liukusäädin + + + spin box + askellusruutu + + + Split + Jaa + + + split bar + jakopalkki + + + split box + jakoruutu + + + Start button + Käynnistä-painike + + + StartUp folder + Käynnistys-kansio + + + status bar + tilarivi + + + Stop + Pysäytä + + + tab control + välilehti + ohjausobjekti + + + task bar + tehtäväpalkki + + + task-oriented Help + tehtäväohje + + + template + malli + + + text box + muokkausruutu + + + title bar + otsikkorivi + + + title text + otsikkoteksti + + + toggle key + tilanvaihtonäppäin + + + toolbar + työkalurivi + + + tooltip + työkaluvihje + + + tree view control + puunäyttö + ohjausobjekti + + + type + tyyppi + noun + + + type + laji + noun + + + type + kirjoittaa + verb + + + unavailable + ei käytettävissä + + + Undo + Kumoa + + + Uninstall + Pura asennus + + + View + Näytä-valikko + + + visual editing + visuaalinen muokkaus + + + well control + graafisen valinnan ohjausobjekti + + + What's This? + Lisätietoja + + + Window + Ikkuna-valikko + + + window + ikkuna + + + Windows Explorer + Resurssienhallinta + + + wizard + ohjattu toiminto + + + workbook + työkirja + + + workgroup + työryhmä + + + workspace + työtila + + + Yes + Kyllä + + diff --git a/tools/linguist/phrasebooks/french.qph b/tools/linguist/phrasebooks/french.qph new file mode 100644 index 000000000..569f7bacf --- /dev/null +++ b/tools/linguist/phrasebooks/french.qph @@ -0,0 +1,1104 @@ + + + About + A propos + + + access key + touche d'accès rapide + + + accessibility + accessibilité + + + action handle + handle d'action + + + active + actif + + + active + active + + + active end + point de fin de sélecion + + + active object + objet actif + + + active window + fenêtre activ + + + adornment + barre + + + Always on Top + Toujours visible + + + anchor point + point de début de sélection + + + Apply + Appliquer + + + auto-exit + sortie automatique + + + auto-repeat + répétition automatique + + + automatic link + Liaison automatique + + + automatic scrolling + défilement automatique + + + autoscroll + défilement automatique + + + Back + Précédent + + + barrel button + Bouton du stylet + + + barrel-tap + toucher-maintenir enfoncé + + + boxed edit + édition contrôlée + control + + + Browse + Parcourir + + + Cancel + Annuler + + + cascading menu + menu en cascade + + + check box + case à cocher + + + check mark + coche + + + child window + fenêtre enfant + + + choose + choisir + + + click + cliquer sur + verb, à l'écran + + + click + clic + noun + + + click + cliquer le + verb, bouton souris + + + Clipboard + Presse-papiers + + + Close + Fermer + + + Close + Fermeture + + + Close button + Fermer + + + collapse + réduire + outline + + + column heading + en-tête de colonne + control + + + combo box + zone de liste modifiable + + + command button + bouton de commande + + + container + conteneur + d'objets + + + context-sensitive Help + aide contextuelle + + + contextual + contextuelle + + + contextual + contextuel + + + control + contrôle + + + Copy + Copier + + + Copy here + Copier ici + + + Create Shortcut + Copier un raccourci + + + Create Shortcut Here + Copier un raccourci ice + + + Cut + Couper + + + default + par défaut + + + default button + bouton par défaut + + + Delete + Supprimer + + + desktop + bureau + + + destination + destination + + + dialog box + boîte de dialogue + + + disability + incapacité + + + disjoint selection + sélection d'objets disjoints + + + dock + aligner + + + document + document + + + double-click + cliquer deux fois + + + double-tap + toucher deux fois + + + drag + faire glisser + + + drag-and-drop + glisser-déplacer + + + drop-down combo box + zone de liste déroulante modifiable + + + drop-down list box + zone de liste déroulante fixe + + + drop-down menu + menu déroulant + + + Edit + Edition + + + Edit menu + modifier + + + ellipsis + points de suspension + + + embedded object + objet incorporé + + + Exit + Quitter + + + expand + développer + an outline + + + Explore + Explorer + + + extended selection + sélection étendue + + + extended selection list box + zone de liste à sélection étendue + + + File + Fichier + menu + + + file + fichier + + + Find + Rechercher + + + Find Next + Suivant + + + Find What + Rechercher + + + folder + dossier + + + font + police + + + font size + taille de police + + + font style + style de police + + + function key + touche de fonction + + + gesture + signe + + + glyph + glyphe + + + group box + zone de groupe + + + handle + handle + + + Help + ? + menu + + + Help + Aide + + + Hide + Masquer + + + hierarchical selection + sélection hiérarchique + + + hold + maintenir + + + hot spot + point d'impact + + + hot zone + zone critique + + + icon + icône + + + inactive + inactive + + + inactive + inactif + + + inactive window + fenêtre inactive + + + ink + dessin à main levée + + + ink edit + éditeur de dissin à main levée + + + input focus + zone d'interaction + + + Insert + Insertion + + + Insert Object + Insérer un objet + + + insertion point + point d'insertion + + + italic + italique + + + label + nom de volume + + + label + étiquette + + + landscape + paysage + + + lasso-tap + toucher lasso + + + lens + loupe + control + + + link + lier + verb + + + link + liaison + noun + + + Link Here + Lier ici + + + list box + zone de liste + + + list view + presentación de iconos + control + + + list view + Liste icônes + control + + + manual link + liaison manuelle + + + Maximize + Agrandissement + + + maximize button + agrandir + + + MDI + MDI + + + menu + menu + + + menu bar + barre de menus + + + menu button + bouton de menus + + + menu item + élément de menu + + + menu title + titre de menu + + + message box + boîte de message + + + Minimize + Réduction + + + minimize button + réduire + + + mixed-value + valeurs multiples + + + modal + modal + + + mode + mode + + + modeless + non modal + + + modifier key + touche de modification + + + mouse + souris + + + Move + Déplacement + + + Move Here + Transférer ici + + + Multiple Document Interface + Interface documents multiples + + + multiple selection list box + zone de liste à sélection multiple + + + My Computer + Poste de travail + icon + + + Network Neighborhood + Voisinage réseau + icon + + + New + Nouveau + + + Next + Suivant + + + object + objet + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + glisser-déplacer OLE + + + OLE embedded object + Objet OLE incorporé + + + OLE linked object + Objet OLE lié + + + OLE nondefault drag and drop + glisser-déplacer OLE non standard + + + Open + Ouvrir + + + Open With + Ouvrir avec + + + option button + case d'option + + + option-set + état des caractéristiques + + + package + ensemble + + + Page Setup + Mise en page + + + palette window + palette + + + pane + volet + + + parent window + fenêtre parent + + + password + mot de passe + + + Paste + Coller + + + Paste Link + Coller avec liaison + + + Paste Shortcut + Coller le raccourci + + + Paste Special + Collage spécial + + + path + chemin + + + Pause + Pause + + + pen + stylet + + + Play + Exécuter + + + Plug and Play + Plug and Play + + + point + point + noun + + + point + amener le pointeur sur + verb + + + pointer + pointeur + + + pop-up menu + menu autonome + + + pop-up window + fenêtre autonome + + + portrait + portrait + + + press + appuyer + and hold a mouse button/et maintenir enfoncé + + + press + appuyer + a key/sur une touche + + + primary container + contenuer principale + + + primary window + fenêtre principale + + + Print + Imprimer + + + printer + imprimante + + + progress indicator + indicateur d'état + control + + + project + projet + + + Properties + Propriétés + + + property inspector + inspecteur de propriétés + + + property page + page de propriétés + + + property sheet + feuille de propriétés + + + property sheet control + feuille de propriétés + + + Quick View + Aperçu + + + read-only + en lecture seule + + + recognition + reconnaissance + + + Recycle Bin + Corbeille + Icon + + + Redo + Annuler Annuler + + + region selection + sélection par zone + + + registry + base des registres + + + Repeat + Répéter + + + Replace + Remplacer + + + Restore + Restauration + + + Restore button + Restaurer + + + Resume + Reprendre + + + Retry + Essayer de nouveau + + + rich-text box + zone de texte RTF + Rich Text Format + + + Run + Exécuter + + + Save + Enregistrer + + + Save as + Enregistrer sous + + + scroll + faire défiler + + + scroll arrow + flèche de défilement + + + scroll bar + barre de défilement + + + scroll box + curseur de défilement + + + secondary window + fenêtre secondaire + + + select + sélectionner + + + Select All + Tout sélectionner + + + selection + sélection + + + selection handle + handle de sélection + + + Send To + Envoyer vers + + + separator + séparateur + + + Settings + Paramètres + + + Setup + Installation + + + Setup + INSTALL + + + shortcut + raccourci + + + shortcut button + raccourci + + + shortcut icon + raccourci + + + shortcut key + touche de raccourci + + + shortcut key control + touche de raccourci + + + Show + Afficher + + + Shutdown + Arrêter l'ordinateur + + + single selection list box + zone de liste à sélection unique + + + Size + Dimension + + + size grip + poignée de redimensionnement + + + slider + défileur + + + spin box + compteur + + + Split + Fractionner + + + split bar + barre de fractionnement + + + split box + curseur de fractionnement + + + Start button + Démarrer + + + StartUp folder + dossier de démarrage + + + status bar + barre d'état + + + Stop + Arrêter + + + tab control + onglet + + + tap + toucher + + + task bar + barre des tâches + + + task-oriented Help + aide spécifique aux tâches + + + template + modèle + + + text box + zone de texte + + + title bar + barre de titre + + + title text + texte de la barre de titre + + + toggle key + touche bascule + + + toolbar + barre d'outils + + + tooltip + info-bulle + + + tree view control + arborescencel + + + type + type + noun + + + type + taper + verb + + + unavailable + pas disponible + + + Undo + Annuler + + + Uninstall + Désinstaller + + + View + Affichage + + + visual editing + activation sur place + + + well control + sélection graphique + + + What's This? + Qu'est-ce que c'est? + + + Window + Fenêtre + + + window + fenêtre + + + Windows Explorer + Explorateur Windows + + + wizard + assistant + + + workbook + classeur + + + workgroup + groupe de travail + + + workspace + espace de travail + + + Yes + Oui + + diff --git a/tools/linguist/phrasebooks/german.qph b/tools/linguist/phrasebooks/german.qph new file mode 100644 index 000000000..9149942ef --- /dev/null +++ b/tools/linguist/phrasebooks/german.qph @@ -0,0 +1,1075 @@ + + + About + Info + + + access key + Zugriffstaste + + + accessibility + Eingabehilfe + + + action handle + Aktionspunkt + + + active + Aktiv + + + active end + Aktives Ende + + + active object + Aktives Objekt + + + active window + Aktives Fenster + + + adornment + Zubehör + + + Always on Top + Immer im Vordergrund + + + anchor point + Ankerpunkt + + + Apply + Zuweisen + + + auto-exit + Textfeld mit automatischer Freigabe + + + auto-repeat + Automatische Wiederholung + + + automatic link + Automatische OLE-Verknüpfung + + + automatic scrolling + Automatischer Bildlauf + + + autoscroll + Automatischer Bildlauf + + + Back + Zurück + + + barrel button + Pen-Knopf + pen + + + barrel-tap + Tippen mit Pen-Knopf + + + boxed edit + Texteditor + control/Steuerelement + + + Browse + Durchsuchen + + + Cancel + Abbrechen + + + cascading menu + Überlappendes Menü + + + check box + Kontrollkästchen + + + check mark + Markierung + Kontrollkästchen + + + child window + Untergeordnetes Fenster + + + choose + Wählen + + + click + Klicken + + + Clipboard + Zwischenablage + + + Close + Schließen + + + Close button + Schließen + Schaltfläche + + + collapse + Ausblenden + outline/Gliederung + + + column heading + Spaltenüberschrift + control/Steuerelement + + + combo box + Kombinationsfeld + + + command button + Schaltfläche + + + container + Container + + + context-sensitive Help + Kontextbezogene Hilfe + + + contextual + Kontextbezogen + + + control + Steuerelement + + + Copy + Kopieren + + + Copy here + Hierher kopieren + + + Create Shortcut + Verknüpfung erstellen + + + Create Shortcut Here + Hiermit verknüpfen + + + Cut + Ausschneiden + + + default + Standard + + + default button + Standardschaltfläche + + + Delete + Löschen + + + desktop + Desktop + + + destination + Ziel + + + dialog box + Dialogfeld + + + disability + Behinderung + + + disjoint selection + Nichtzusammenhängende Auswahl + + + dock + Verankern + + + document + Dokument + + + double-click + Doppelklicken + + + double-tap + Doppeltippen + + + drag + Ziehen + + + drag-and-drop + Drag & Drop + + + drop-down combo box + Dropdown-Kombinationsfeld + + + drop-down list box + Dropdown-Listenfeld + + + drop-down menu + Dropdown-Menü + + + Edit + Bearbeiten + + + Edit + Bearbeiten + menu/Menü + + + ellipsis + Auslassungspunkte + + + embedded object + Eingebettetes + + + Exit + Beenden + + + expand + Einblenden + an outline/einer Struktur + + + Explore + Explorer + Befehl + + + extended selection + Erweiterte Auswahl + + + extended selection list box + Listenfeld für erweiterte Auswahl + + + File + Datei + menu + + + file + Datei + + + Find + Suchen + + + Find Next + Weitersuchen + + + Find What + Suchen nach + + + folder + Ordner + + + font + Schriftart + + + font size + Schriftgrad + + + font style + Schriftschnitt + + + function key + Funktionstaste + + + gesture + Schriftzug + + + glyph + Zeichen + + + group box + Gruppenfeld + + + handle + Ziehpunkt + + + Help + ? + menu + + + Help + Hilfe + + + Hide + Ausblenden + + + hierarchical selection + Hierarchische Auswahl + + + hold + Halten + + + hot spot + Hot Spot + + + hot zone + Hot Zone + + + icon + Symbol + + + inactive + Inaktiv + + + inactive window + Inaktives Fenster + + + ink + Ink + + + ink edit + Inkeditor + + + input focus + Eingabefokus + + + Insert + Einfügen + Menü + + + Insert Object + Objekt einfügen + + + insertion point + Einfügemarke + + + italic + Kursiv + + + label + Bezeichnung + + + landscape + Querformat + + + lasso-tap + Lasso-tippen + + + lens + Lupe + control + + + link + Verknüpfung + noun + + + link + Verknüpfen + verb + + + Link Here + Hiermit verknüpfen + + + list box + Listenfeld + + + list view + Listenansicht + control + + + manual link + Manuelle OLE-Verknüpfung + + + Maximize + Maximieren + + + maximize button + Maximieren + Schaltfläche + + + MDI + MDI + + + menu + Menü + + + menu bar + Menüleiste + + + menu button + Menü + Schaltfläche + + + menu item + Menüelement + + + menu title + Menütitel + + + message box + Meldungsfeld + + + Minimize + Minimieren + + + minimize button + Minimieren + Schaltfläche + + + mixed-value + Gemischt + + + modal + Modal + + + mode + Modus + + + modeless + Interaktiv + + + modifier key + Zusatztaste + + + mouse + Maus + + + Move + Verschieben + + + Move Here + Hierher verschieben + + + Multiple Document Interface + MDI + Multiple Document Interface + + + multiple selection list box + Listenfeld für Mehrfachauswahl + + + My Computer + Arbeitsplatz + icon/Symbol + + + Network Neighborhood + Netzwerk + icon/Symbol + + + New + Neu + + + Next + Weiter + + + object + Objekt + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + OLE-Drag & Drop + + + OLE embedded object + Eingebettetes OLE-Objekt + + + OLE linked object + Verknüpftes OLE-Objekt + + + OLE nondefault drag and drop + Vom Standard abweichendes OLE-Drag & Drop + + + OLE nondefault drag and drop + Aangepast slepen en neerzetten via OLE + + + Open + Öffnen + + + Open With + Öffnen mit + + + option button + Optionsfeld + + + option-set + Aktivierte Option + + + package + Paket + + + Page Setup + Seite einrichten + + + palette window + Palettenfenster + + + pane + Fensterbereich + + + parent window + Übergeordnetes Fenster + + + password + Kennwort + + + Paste + Einfügen + + + Paste Link + Verknüpfung einfügen + + + Paste Shortcut + Verknüpfung einfügen + + + Paste Special + Inhalte einfügen + + + path + Pfad + + + Pause + Anhalten + + + pen + Pen + + + Play + Wiedergeben + + + Plug and Play + Plug & Play + + + point + Zeigen + + + pointer + Zeiger + + + pop-up menu + Kontextmenü + + + pop-up window + Popup-Fenster + + + portrait + Hochformat + + + press + Drücken + and hold a mouse button/und Halten einer Maustaste + + + press + Drücken + a key/einer Taste + + + primary container + Primär-Container + + + primary window + Primärfenster + + + Print + Drucken + + + printer + Drucker + + + progress indicator + Statusanzeige + control + + + project + Projekt + + + Properties + Eigenschaften + + + property inspector + Eigenschaftenanzeige + + + property page + Eigenschaftengruppe + + + property sheet + Eigenschaftenfenster + + + property sheet control + Eigenschaftenfenster-Steuerelement + + + Quick View + Schnellansicht + + + read-only + Schreibgeschützt + + + recognition + Schrifterkennung + + + Recycle Bin + Papierkorb + Icon/Symbol + + + Redo + Wiederherstellen + + + region selection + Bereichsauswahl + + + registry + Registrierung + + + Repeat + Wiederholen + + + Replace + Ersetzen + + + Restore + Wiederherstellen + + + Restore button + Wiederherstellen + Schaltfläche + + + Resume + Fortsetzen + + + Retry + Wiederholen + + + rich-text box + RTF-Textfeld + + + Run + Ausführen + + + Save + Speichern + + + Save as + Speichern unter + + + scroll + Bildlauf durchführen + + + scroll arrow + Bildlaufpfeil + + + scroll bar + Bildlaufleiste + + + scroll box + Bildlauffeld + + + secondary window + Sekundärfenster + + + select + Auswählen + + + Select All + Alle markieren + + + selection + Auswahl + + + selection handle + Auswahlpunkt + + + Send To + Senden an + + + separator + Trennelement + + + Settings + Einstellungen + + + Setup + Einrichten + + + shortcut + Verknüpfung + + + shortcut button + Verknüpfte Schaltfläche + + + shortcut icon + Verknüpfungssymbol + + + shortcut key + Tastenkombination + + + shortcut key control + Steuerelement für Tastenbelegung + + + Show + Anzeigen + + + Shutdown + Beenden + + + single selection list box + Listenfeld für Einfachauswahl + + + Size + Größe ändern + + + size grip + Element für Größenänderung + + + slider + Schieber + + + spin box + Drehfeld + + + Split + Teilen + + + split bar + Fensterteiler + + + split box + Teilungsfeld + + + Start button + Start + Schaltfläche + + + StartUp folder + Autostart + Ordner + + + status bar + Statusleiste + + + Stop + Beenden + + + tab control + Register + + + tap + Tippen + + + task bar + Task-Leiste + + + task-oriented Help + Vorgangsbezogene Hilfe + + + template + Vorlage + + + text box + Textfeld + + + title bar + Titelleiste + + + title text + Titeltext + + + toggle key + Ein-/Aus-Taste + + + toolbar + Symbolleiste + + + tooltip + QuickInfo + + + tree view control + Strukturansicht + + + type + Eingeben + verb + + + type + Typ + noun + + + unavailable + Nicht verfügbar + + + Undo + Rückgängig + + + Uninstall + Deinstallieren + + + View + Ansicht + Menü + + + visual editing + Direkte Bearbeitung + + + well control + Steuerelement zur Grafikanzeige + + + What's This? + Direkthilfe + + + Window + Fenster + Menü + + + window + Fenster + + + Windows Explorer + Explorer + + + wizard + Assistent + + + workbook + Arbeitsmappe + + + workgroup + Arbeitsgruppe + + + workspace + Arbeitsbereich + + + Yes + Ja + + diff --git a/tools/linguist/phrasebooks/italian.qph b/tools/linguist/phrasebooks/italian.qph new file mode 100644 index 000000000..2aa3d7a40 --- /dev/null +++ b/tools/linguist/phrasebooks/italian.qph @@ -0,0 +1,1105 @@ + + + About + Informazioni su + + + access key + tasto di scelta + + + accessibility + accesso facilitato + + + action handle + identificatore dell'azione + + + active + attivo + + + active end + punto finale + + + active object + oggetto attivo + + + active window + finestra attiva + + + adornment + barra + + + Always on Top + Sempre in primo piano + + + anchor point + punto di ancoraggio + + + Apply + Applica + + + auto-exit + ad uscita automatica + + + auto-repeat + a ripetizione automatica + + + automatic link + collegamento automatico + + + automatic scrolling + scorrimento automatico + + + autoscroll + scorrimento automatico + + + Back + Indietro + + + barrel button + pulsante della penna + pen + + + barrel-tap + tocco con il pulsante premuto + + + boxed edit + casella di testo a griglia + control + + + Browse + Sfoglia + + + Cancel + Annulla + + + cascading menu + menu sovrapposto + + + check box + casella di controllo + + + check mark + segno di spunta + + + child window + finestra secondaria + + + choose + scegliere + + + click + fare clic + + + Clipboard + Appunti + + + Close + Chiudi + + + Close button + pulsante di chiusura + + + collapse + comprimere + outline, verb + + + column heading + intestazione di colonna + control + + + combo box + casella combinata + + + command button + pulsante di comando + + + container + contenitore + + + context-sensitive Help + guida sensibile al contesto + + + contextual + contestuale + + + control + controllo + + + Copy + Copia + + + Copy here + Copia + + + Create Shortcut + Crea collegamento + + + Create Shortcut Here + Crea collegamento + + + Cut + Taglia + + + default + predefinito + + + default button + pulsante predefinito + + + Delete + Elimina + + + desktop + desktop + + + destination + destinazione + + + dialog box + finestra di dialogo + + + disability + disabilità + + + disjoint selection + selezione multipla + + + dock + posizionare + + + document + documento + + + double-click + doppio clic + noun + + + double-click + fare doppio clic + verb + + + double-tap + toccare due volte in rapida successione + verb + + + double-tap + doppio tocco + noun + + + drag + trascinare + + + drag-and-drop + trascinare e rilasciare + verb + + + drag-and-drop + caratteristica Trascina selezione + noun + + + drop-down combo box + casella combinata a discesa + + + drop-down list box + casella di riepilogo a discesa + + + drop-down menu + menu a discesa + + + Edit + Modifica + + + Edit menu + menu Modifica + + + ellipsis + puntini di sospensione + + + embedded object + oggetto incorporato + + + Exit + Esci + + + expand + espandere + an outline/una struttura + + + Explore + Gestione risorse + + + extended selection + selezione estesa + + + extended selection list box + casella di riepilogo a selezione estesa + + + file + file + + + File menu + menu File + + + Find + Trova + + + Find Next + Trova successivo + + + Find What + Trova + + + folder + cartella + + + font + tipo di carattere + + + font size + dimensione carattere + + + font style + stile carattere + + + function key + tasto funzione + + + gesture + segno + + + glyph + icona + + + group box + casella di gruppo + + + handle + quadratino di ridimensionamento + noun + + + Help + Guida + + + Help menu + menu ? + + + Hide + Nascondi + + + hierarchical selection + selezione gerarchica + + + hold + tenere premuto + + + hot spot + area sensibile del puntatore + + + hot zone + area sensibile dell'oggetto + + + icon + icona + + + inactive + inattivo + + + inactive window + finestra inattiva + + + ink + tratto + + + ink edit + modifica tratto + + + input focus + elemento attivo + + + Insert + menu Inserisci + + + Insert Object + Inserisci oggetto + + + insertion point + punto di inserimento + + + italic + corsivo + + + label + etichetta + + + landscape + orizzontale + + + lasso-tap + selezione circolare + + + lens + lente + control + + + link + collegamento + noun + + + link + collegare + verb + + + Link Here + Collega + + + list box + casella di riepilogo + + + list view + visualizzazione elementi + control + + + manual link + collegamento manuale + + + Maximize + Ingrandisci + + + maximize button + pulsante di ingrandimento + + + MDI + MDI + + + menu + menu + + + menu bar + barra dei menu + + + menu button + pulsante menu + + + menu item + voce di menu + + + menu title + titolo di menu + + + message box + finestra di messaggio + + + Minimize + Riduci a icona + + + minimize button + pulsante di riduzione ad icona + + + mixed-value + valori misti + + + modal + a scelta obbligatoria + + + mode + modalità + + + modeless + non a scelta obbligatoria + + + modifier key + tasto di modifica delle funzioni di tastiera + + + modifier key + tasto di modifica dell'output di tastiera + + + mouse + mouse + + + Move + Sposta + + + Move Here + Sposta + + + Multiple Document Interface + interfaccia a documenti multipli + + + multiple selection list box + casella di riepilogo a selezione multipla + + + My Computer + Risorse del computer + icon/icono + + + Network Neighborhood + Risorse di rete + icon + + + New + Nuovo + + + Next + Avanti + + + object + oggetto + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + caratteristica Trascina selezione + + + OLE embedded object + oggetto incorporato OLE + + + OLE linked object + oggetto collegato OLE + + + OLE nondefault drag and drop + caratteristica Trascina selezione OLE non predefinita + + + Open + Apri + + + Open With + Apri con + + + option button + pulsante di opzione + + + option-set + opzione impostata + + + option-set + opzione attivata + + + package + package + + + Page Setup + Imposta pagina + + + palette window + casella degli tavolozza di colori + + + palette window + casella degli strumenti + + + pane + riquadro + + + parent window + finestra principale + + + password + password + + + Paste + Incolla + + + Paste Link + Incolla collegamento + + + Paste Shortcut + Incolla collegamento + + + Paste Special + Incolla speciale + + + path + percorso + + + Pause + Interrompi + + + pen + penna + + + Play + Riproduci + + + Plug and Play + Plug and Play + + + point + punto + + + pointer + puntatore + + + pop-up menu + menu di scelta rapida + + + pop-up window + finestra popup + + + portrait + verticale + + + press + premere + a key/un tasto + + + press + premere + and hold a mouse button/e tenere premuto un pulsante del mouse + + + primary container + contenitore principale + + + primary window + finestra principale + + + Print + Stampa + + + printer + stampante + + + progress indicator + indicatore di avanzamento del processo + control + + + project + progetto + + + Properties + Proprietà + + + property inspector + visualizzatore proprietà + + + property page + scheda proprietà + + + property sheet + finestra proprietà + + + property sheet control + controllo finestra proprietà + + + Quick View + Anteprima + + + read-only + sola lettura + + + recognition + riconoscimento + + + Recycle Bin + Cestino + Icon + + + Redo + Ripeti + + + region selection + selezione dell'area + + + registry + registro di configurazione + + + Repeat + Ripeti + + + Replace + Sostituisci + + + Restore + Ripristina + + + Restore button + pulsante di ripristino + + + Resume + Riprendi + + + Retry + Riprova + + + rich-text box + casello di testo RTF + + + Run + Esegui + + + Save + Salva + + + Save as + Salva con nome + + + scroll + scorrere + verb + + + scroll arrow + freccia di scorrimento + + + scroll bar + barra di scorrimento + + + scroll box + casella di scorrimento + + + secondary window + finestra secondaria + + + select + selezionare + verb + + + Select All + Seleziona tutto + + + selection + selezione + + + selection handle + quadratino di selezione + + + Send To + Invia a + + + separator + separatore + + + Settings + Impostazioni + + + Setup + Imposta + + + shortcut + collegamento + + + shortcut button + pulsante di collegamento + + + shortcut icon + icona di collegamento + + + shortcut key + tasto di scelta rapida + + + shortcut key control + controllo tasto di scelta rapida + + + Show + Mostra + + + Shutdown + Chiudi sessione + comando del menu Avvio + + + Shutdown + Arresta il sistema + pulsanti e opzioni + + + single selection list box + casella di riepilogo a selezione singola + + + Size + Dimensione + + + size grip + punto di ridimensionamento + + + slider + dispositivo di scorrimento + + + spin box + casella di selezione + + + Split + Dividi + + + split bar + barra di divisione + + + split box + casella di divisione + + + Start button + pulsante Avvio + + + StartUp folder + cartella Esecuzione automatica + + + status bar + barra di stato + + + Stop + Ferma + + + tab control + controllo a schede + + + tap + toccare + verb + + + tap + tocco + noun + + + task bar + barra delle applicazioni + + + task-oriented Help + guida orientata alle attività + + + template + modello + + + text box + casella di testo + + + title bar + barra del titolo + + + title text + testo della barra del titolo + + + toggle key + tasto interruttore + + + toolbar + barra degli strumenti + + + tooltip + descrizione comando + + + tree view control + controllo per la visualizzazione ad albero + + + type + inserire + verb + + + type + digitare + verb + + + type + tipo + noun + + + unavailable + non disponibile + + + Undo + Annulla + + + Uninstall + Rimozione + + + View + menu Visualizza + + + visual editing + modifica diretta + + + well control + controllo di selezione grafica + + + What's This? + Guida rapida + + + Window + menu Finestra + + + window + finestra + + + Windows Explorer + Gestione risorse + + + wizard + installazione guidata + + + workbook + cartella di lavoro + + + workgroup + gruppo di lavoro + + + workspace + area di lavoro + + + Yes + + + diff --git a/tools/linguist/phrasebooks/norwegian.qph b/tools/linguist/phrasebooks/norwegian.qph new file mode 100644 index 000000000..d01187cfe --- /dev/null +++ b/tools/linguist/phrasebooks/norwegian.qph @@ -0,0 +1,1004 @@ + + + About + Om + + + access key + tilgangstast + + + accessibility + tilgjengelighet + + + action handle + handlingshåndtak + + + active + aktiv + + + active end + markeringsavslutning + + + active object + aktivt objekt + + + active window + aktivt vindu + + + adornment + verktøyselement + + + Always on Top + Alltid øverst + + + anchor point + forankringspunkt + + + Apply + Bruk + + + auto-exit + automatisk avslutning + + + auto-repeat + automatisk gjentagelse + + + automatic link + automatisk kobling + + + automatic scrolling + automatisk rulling + + + autoscroll + autorulling + + + Back + Tilbake + + + Browse + Bla gjennom + + + Cancel + Avbryt + + + cascading menu + undermeny + + + check box + avmerkingsboks + + + check mark + merke + + + child window + undervindu + + + choose + velge + + + click + klikke + + + Clipboard + utklippstavle + + + Close + Lukk + + + Close button + lukkeknapp + + + collapse + skjule + outline/disposisjon + + + column heading + kolonneoverskrift + control/kontroll + + + combo box + kombinasjonsboks + + + command button + kommandoknapp + + + container + beholder + + + context-sensitive Help + kontekstavhengig hjelp + + + contextual + kontekstavhengig + + + control + kontroll + + + Copy + Kopier + + + Copy here + Kopier hit + + + Create Shortcut + Lag snarvei + + + Create Shortcut Here + Lag snarvei her + + + Cut + Klipp ut + + + default + standard + + + default button + standardknapp + + + Delete + Slett + + + desktop + skrivebord + + + destination + mål + + + dialog box + dialogboks + + + disability + funksjonshemning + + + disjoint selection + ikke sammenhengende utvalg + + + dock + forankre + + + document + dokument + + + double-click + dobbeltklikke + + + drag + dra + + + drag-and-drop + dra och slippe + + + drop-down combo box + kombinasjonsboks + + + drop-down list box + rullegardinliste + + + drop-down menu + rullegardinmeny + + + Edit + Rediger + + + Edit menu + Rediger-menyen + + + ellipsis + ellipse + + + embedded object + innebygd objekt + + + Exit + Avslutt + + + expand + utvide + an outline/en disposisjon + + + Explore + Utforsk + + + extended selection + utvidet merking + + + extended selection list box + liste med utvidet merking + + + file + fil + + + File menu + Fil-menyen + + + Find + Søk etter + + + Find Next + Søk etter neste + + + Find What + Søk etter + + + folder + mappe + + + font + skrift + + + font size + skriftstørrelse + + + font style + skriftstil + + + function key + funksjonstast + + + group box + gruppeboks + + + handle + håndtak + + + Help + Hjelp + + + Help menu + Hjelp-menyen + + + Hide + Skjul + + + hierarchical selection + hierarkisk merking + + + hold + holde + + + hot spot + fokus + + + hot zone + fokuseringssone + + + icon + ikon + + + inactive + inaktiv + + + inactive window + inaktivt vindu + + + input focus + indatafokus + + + Insert + Sett inn-menyen + + + Insert Object + Sett inn objekt + + + insertion point + innsettingspunkt + + + italic + kursiv + + + label + etikett + + + landscape + liggende + + + link + koble + verb + + + link + kobling + noun + + + Link Here + Lag kobling her + + + list box + listeboks + + + list view + listevisning + control/kontroll + + + manual link + manuell kobling + + + Maximize + Maksimer + + + maximize button + maksimeringsknapp + + + MDI + MDI + + + menu + meny + + + menu bar + menylinje + + + menu button + menyknapp + + + menu item + menyelement + + + menu title + menytittel + + + message box + meldingsboks + + + Minimize + Minimer + + + minimize button + minimeringsknapp + + + mixed-value + blandet verdi + + + modal + modal + + + mode + modus + + + modeless + icke-modal + + + modifier key + modifiseringstast + + + mouse + mus + + + Move + Flytt + + + Move Here + Flytt hit + + + Multiple Document Interface + flerdokumentgrensesnitt + + + multiple selection list box + flervalgsliste + + + My Computer + Min datamaskin + icon/ikon + + + Network Neighborhood + Andre maskiner + icon/ikon + + + New + Ny + + + Next + Neste + + + object + objekt + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + OLE dra og slipp + + + OLE embedded object + innebyggd OLE-objekt + + + OLE linked object + koblet OLE-objekt + + + OLE nondefault drag and drop + utvidet OLE dra og slipp + + + Open + Åpne + + + Open With + Åpne i + + + option button + alternativknapp + + + option-set + valgt alternativ + + + package + pakke + + + Page Setup + Utskriftsformat + + + palette window + palettvindu + + + pane + rute + + + parent window + hovedvindu + + + password + passord + + + Paste + Lim inn + + + Paste Link + Lim inn kobling + + + Paste Shortcut + Lim inn snarvei + + + Paste Special + Lim inn utvalg + + + path + bane + + + Pause + Pause + + + Play + Spill + + + Plug and Play + Plug and Play + + + point + punkt + + + point + peke + + + pointer + peker + + + pop-up menu + hurtigmeny + + + pop-up window + forklaringsvindu + + + portrait + stående + + + press + klikke + and hold a mouse button/og holde nede en musetast + + + press + trykke + a key/en tast + + + primary container + primærbeholder + + + primary window + primærvindu + + + Print + Skriv ut + + + printer + skriver + + + progress indicator + fremdriftsindikator + control/kontroll + + + project + prosjekt + + + Properties + Egenskaper + + + property inspector + egenskapsvisning + + + property page + egenskapsside + + + property sheet + egenskapsark + + + property sheet control + egenskapsarkkontroll + + + Quick View + Hurtigvisning + + + read-only + skrivebeskyttet + + + Recycle Bin + Papirkurv + Icon/ikon + + + Redo + Gjør om + + + region selection + områdemerking + + + registry + register + + + Repeat + Gjenta + + + Replace + Erstatt + + + Restore + Gjenopprett + + + Restore button + gjenopprettingsknapp + + + Resume + Fortsett + + + Retry + Prøv på nytt + + + rich-text box + boks for rik tekst + + + Run + Kjør + + + Save + Lagre + + + Save as + Lagre som + + + scroll + rulle + + + scroll arrow + rullepil + + + scroll bar + rullefelt + + + scroll box + rulleboks + + + secondary window + sekundærvindu + + + select + merke + + + Select All + Merk alt + + + selection + merket område + + + selection handle + markeringshåndtak + + + Send To + Send til + + + separator + skilletegn + + + Settings + Innstillinger + + + Setup + Installasjon + + + shortcut + snarvei + + + shortcut button + snarveisknapp + + + shortcut icon + snarveisikon + + + shortcut key + hurtigtast + + + shortcut key control + hurtigtastkontroll + + + Show + Vis + + + Shutdown + Avslutt + + + single selection list box + enkeltvalgsliste + + + Size + Størrelse + + + size grip + skaleringshåndtak + + + slider + glidebryter + + + spin box + verdisettingsboks + + + Split + Del + + + split bar + delelinje + + + split box + deleboks + + + Start button + startknapp + + + StartUp folder + Oppstart-mappen + + + status bar + statuslinje + + + Stop + Stopp + + + tab control + kategorikontroll + + + task bar + oppgavelinje + + + task-oriented Help + oppgaveorientert hjelp + + + template + mal + + + text box + tekstboks + + + title bar + tittellinje + + + title text + titteltekst + + + toggle key + veksletast + + + toolbar + verktøylinje + + + tooltip + verktøytips + + + tree view control + trevisningskontroll + + + type + skrive + verb + + + type + type + noun + + + unavailable + ikke tilgjengelig + + + Undo + Angre + + + Uninstall + Avinstaller + + + View + Vis-meny + + + visual editing + visuell redigering + + + well control + grafikkontroll + + + What's This? + Hva er dette? + + + Window + Vindu-menyen + + + window + vindu + + + Windows Explorer + Windows Utforsker + + + wizard + veiviser + + + workbook + arbeidsbok + + + workgroup + arbeidsgruppe + + + workspace + arbeidsområde + + + Yes + Ja + + diff --git a/tools/linguist/phrasebooks/russian.qph b/tools/linguist/phrasebooks/russian.qph new file mode 100644 index 000000000..ec64aae65 --- /dev/null +++ b/tools/linguist/phrasebooks/russian.qph @@ -0,0 +1,982 @@ + + + About + О программе + + + access key + горячая клавиша + + + accessibility + удобство + + + action handle + управление поведением + + + active + активный + + + active end + окончание выбора + + + active object + активный объект + + + active window + активное окно + + + adornment + украшение + + + Always on Top + Всегда наверху + + + anchor point + точка начала выбора + + + Apply + Применить + + + auto-exit + автоматический выход + + + auto-repeat + авто-повтор + + + automatic link + автоматическое связывание + + + automatic scrolling + автоматическая прокрутка + + + autoscroll + авто-прокрутка + + + Back + Назад + + + boxed edit + окно редактирования + + + Browse + Обзор + + + Cancel + Отмена + + + cascading menu + ниспадающее меню + + + check box + флажок + + + check mark + флажок + + + child window + дочернее окно + + + choose + выбрать + + + click + щелчок + + + Clipboard + Буфер обмена + + + Close + Закрыть + + + Close button + кнопка закрытия + + + collapse + крах + + + column heading + заголовок колонки + + + combo box + поле со списком + + + command button + кнопка + + + container + контейнер + + + context-sensitive Help + контекстная помощь + + + contextual + контекстный + + + control + элемент управления + + + Copy + Копировать + + + Copy here + Копировать сюда + + + Create Shortcut + Создать ярлык + + + Create Shortcut Here + Создать ярлык здесь + + + Cut + Вырезать + + + default + по умолчанию + + + default button + кнопка по умолчанию + + + Delete + Удалить + + + desktop + рабочий стол + + + destination + цель + + + dialog box + окно диалога + + + disability + неспособность + + + disjoint selection + разделить выбранные элементы + + + dock + док + + + document + документ + + + double-click + двойной щелчок + + + drag + перетащить + + + drag-and-drop + drag-and-drop + + + drop-down combo box + раскрыть поле со списком + + + drop-down list box + прокрутить список + + + drop-down menu + открыть меню + + + Edit + Правка + + + Edit menu + меню Правка + + + ellipsis + эллипс + + + embedded object + встроенный объект + + + Exit + Выход + + + expand + расширять + + + Explore + Исследовать + + + extended selection + расширенный выбор + + + extended selection list box + список с расширенным выбором + + + file + файл + + + File menu + меню Файл + + + Find + Поиск + + + Find Next + Продолжить поиск + + + Find What + Поиск + + + folder + каталог + + + font + шрифт + + + font size + размер шрифта + + + font style + стиль шрифта + + + function key + функциональная клавиша + + + glyph + глиф + + + group box + контейнер элементов + + + handle + управление + + + Help + Справка + + + Hide + Скрыть + + + hierarchical selection + иерархический выбор + + + hold + удерживать + + + hot spot + фокус + + + hot zone + активная зона + + + icon + пиктограмма + + + inactive + неактивный + + + inactive window + неактивное окно + + + input focus + фокус ввода + + + Insert + Вставить + + + Insert Object + Вставить объект + + + insertion point + место вставки + + + italic + курсив + + + label + надпись + + + landscape + альбом + + + link + ссылка + + + link + связать + + + Link Here + Создать ссылку здесь + + + list box + список + + + list view + древовидный список + + + manual link + ручное связывание + + + Maximize + Распахнуть + + + maximize button + кнопка максимизации + + + MDI + MDI + + + menu + меню + + + menu bar + строка меню + + + menu button + кнопка меню + + + menu item + элемент меню + + + menu title + заголовок меню + + + message box + окно сообщений + + + Minimize + Свернуть + + + minimize button + кнопка минимизации + + + modal + модальный + + + mode + режим + + + modeless + немодальный + + + modifier key + клавиша-модификатор + + + mouse + мышь + + + Move + Переместить + + + Move Here + Переместить сюда + + + Multiple Document Interface + Multiple Document Interface + + + multiple selection list box + список с множественным выбором + + + My Computer + Мой компьютер + + + Network Neighborhood + Сетевое окружение + + + New + Новый + + + Next + Следующий + + + object + объект + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + OLE-механизм + + + OLE embedded object + внедренный OLE-объект + + + OLE linked object + связанный OLE-объект + + + OLE nondefault drag and drop + предопределенный OLE-механизм + + + Open + Открыть + + + Open With + Открыть с помощью + + + option button + переключатель + + + option-set + набор параметров + + + package + пакет + + + Page Setup + шаг установки + + + palette window + окно выбора палитры + + + pane + панель + + + parent window + родительское окно + + + password + пароль + + + Paste + Вставить + + + Paste Link + Вставить ссылку + + + Paste Shortcut + Вставить ярлык + + + Paste Special + Специальная вставка + + + path + путь + + + Pause + Пауза + + + Play + Воспроизведение + + + Plug and Play + Plug and Play + + + point + пункт + + + pointer + указатель + + + pop-up menu + всплывающее меню + + + pop-up window + всплывающее окно + + + portrait + портрет + + + press + нажимать + + + primary container + корневой контейнер + + + primary window + главное окно + + + Print + Печать + + + printer + принтер + + + progress indicator + индикатор хода процесса + + + project + проект + + + Properties + Свойства + + + property inspector + инспектор свойств + + + property page + страница свойств + + + property sheet + группа свойств + + + property sheet control + управление группой свойств + + + Quick View + Быстрый просмотр + + + read-only + только чтение + + + Recycle Bin + Корзина + + + Redo + Повторить + + + region selection + область выделения + + + registry + реестр + + + Repeat + Повторить + + + Replace + Заменить + + + Restore + Восстановить + + + Restore button + Кнопка восстановления + + + Resume + Продолжить + + + Retry + Повторить + + + rich-text box + окно RTF-редактора + + + Run + Выполнить + + + Save + Сохранить + + + Save as + Сохранить как + + + scroll + прокрутить + + + scroll arrow + кнопка прокрутки + + + scroll bar + полоса прокрутки + + + scroll box + окно с полосами прокрутки + + + secondary window + подчиненное окно + + + select + выбрать + + + Select All + Выделить все + + + selection + выбор + + + selection handle + осуществление выбора + + + Send To + Отправить + + + separator + разделитель + + + Settings + Настройки + + + Setup + Установить + + + shortcut + ярлык + + + shortcut button + кнопка + + + shortcut icon + пиктограмма + + + shortcut key + комбинация клавиш + + + shortcut key control + настройка комбинации клавиш + + + Show + Показать + + + Shutdown + Выключение + + + single selection list box + список с одиночным выбором + + + Size + Размер + + + size grip + уголок для изменения размера + + + slider + ползунок + + + spin box + поле со счетчиком + + + Split + Разделить + + + split bar + разделительная черта + + + split box + разделительная рамка + + + Start button + кнопка Пуск + + + StartUp folder + каталог Автозапуска + + + status bar + статусная строка + + + Stop + Стоп + + + tab control + вкладка + + + task bar + панель задач + + + task-oriented Help + контекстная справка + + + template + шаблон + + + text box + текстовое поле + + + title bar + заголовок + + + title text + текст заголовка + + + toggle key + кнопка-выключатель + + + toolbar + панель инструментов + + + tooltip + всплывающая подсказка + + + tree view control + древовидный список + + + type + тип + + + type + набирать + + + unavailable + недоступный + + + Undo + Отменить + + + Uninstall + Удалить + + + View + Вид + + + visual editing + визуальное редактирование + + + well control + элемент графического интерфейса + + + What's This? + Что это? + + + Window + Окно + + + window + окно + + + Windows Explorer + Проводник Windows + + + wizard + мастер + + + workbook + учебник + + + workgroup + рабочая группа + + + workspace + рабочая область + + + Yes + Да + + diff --git a/tools/linguist/phrasebooks/spanish.qph b/tools/linguist/phrasebooks/spanish.qph new file mode 100644 index 000000000..cebe2b223 --- /dev/null +++ b/tools/linguist/phrasebooks/spanish.qph @@ -0,0 +1,1086 @@ + + + About + Acerca de + + + access key + tecla de acceso + + + accessibility + accesibilidad + + + action handle + controlador de acciones + + + active + activo + + + active end + fin de la selección activa + + + active object + objeto activo + + + active window + ventana activa + + + adornment + opción gráfica + + + Always on Top + Siempre visible + + + anchor point + inicio de la selección activa + + + Apply + Aplicar + + + auto-exit + salida automática + + + auto-repeat + repetición automática + + + automatic link + vínculo automático + + + automatic scrolling + desplazamiento automático + + + autoscroll + desplazamiento automático + + + Back + Atrás + + + barrel button + botón del lápiz + pen + + + barrel-tap + puntenar con el botón presionado + + + boxed edit + edición en casilla + control + + + Browse + Examinar + + + Cancel + Cancelar + + + cascading menu + menú en cascada + + + check box + casilla de verificación + + + check mark + marca de verificación + + + child window + ventana secundaria + + + choose + elegir + + + click + hacer clic + + + Clipboard + Portapapeles + + + Close + Cerrar + + + Close button + botón &quot;Cerrar&quot; + + + collapse + contraer + outline/esquerna + + + column heading + encabezado de columna + control + + + combo box + cuadro combinado + + + command button + botón de comando + + + container + contenedor + + + context-sensitive Help + ayuda interactiva + + + contextual + contextual + + + control + control + + + Copy + Copiar + + + Copy here + Copiar aquí + + + Create Shortcut + Crear acceso directo + + + Create Shortcut Here + Crear acceso directo aquí + + + Cut + Cortar + + + default + predeterminado + + + default button + botón predeterminado + + + Delete + Eliminar + + + desktop + escritorio + + + destination + destino + + + dialog box + cuadro de diálogo + + + disability + Discapacidades + + + disjoint selection + selección disjunta + + + dock + acoplar + + + document + documento + + + double-click + hacer doble clic + + + double-tap + puntear dos veces + + + drag + arrastrar + + + drag-and-drop + arrastrar y colocar + + + drop-down combo box + cuadro combinado desplegable + + + drop-down list box + cuadro de lista desplegable + + + drop-down menu + menú desplegable + + + Edit + Edición + + + Edit menu + menú Edición + + + ellipsis + puntos suspensivos + + + embedded object + objeto incrustado + + + Exit + Salir + + + expand + expandir + an outline/un esquema + + + Explore + Explorar + + + extended selection + selección extendida + + + extended selection list box + cuadro de lista de selección extendida + + + file + archivo + + + File menu + menú Archivo + + + Find + Buscar + + + Find Next + Buscar siguiente + + + Find What + Buscar + + + folder + carpeta + + + font + fuente + + + font size + tamaño de fuente + + + font style + estilo de fuente + + + function key + tecla de función + + + gesture + signo + + + glyph + símbolo gráfico + + + group box + cuadro de grupo + + + handle + controlar + verb + + + handle + controlador + noun + + + Help + Ayuda + + + Help menu + menú Ayuda + + + Hide + Ocultar + + + hierarchical selection + selección jerártquica + + + hold + mantener presionado + + + hot spot + punto interactivo + + + hot zone + zona interactiva + + + icon + icono + + + inactive + inactivo + + + inactive window + ventana inactiva + + + ink + trazo + + + ink edit + editor de trazos + + + input focus + zona de entrada + + + input focus + zona de entrada de datos + + + Insert + menú Insertar + + + Insert Object + Insertar objeto + + + insertion point + punto de inserción + + + italic + cursiva + + + label + etiqueta + + + landscape + horizontal + + + lasso-tap + punteo en la selección + + + lens + lente + control + + + link + vincular + verb + + + link + vínculo + noun + + + Link Here + Vincular aquí + + + list box + cuadro de lista + + + list view + ver lista + control + + + list view + presentación de iconos + control + + + manual link + vínculo manual + + + Maximize + Maximizar + + + maximize button + botón de maximizar + + + MDI + MDI + + + menu + menú + + + menu bar + barra de menús + + + menu button + botón de menú + + + menu item + elemento de menú + + + menu title + título de menú + + + message box + cuadro de mensaje + + + Minimize + Minimizar + + + minimize button + botón de minimizar + + + mixed-value + valores mezclados + + + modal + modal + + + mode + modo + + + modeless + sin modo + + + modifier key + tecla modificadora + + + mouse + mouse + + + Move + Mover + + + Move Here + Mover aquí + + + Multiple Document Interface + interfaz de documentos múltiples + + + multiple selection list box + cuadro de lista de selección múltiple + + + My Computer + Mi PC + icon/icono + + + Network Neighborhood + Entorno de red + icon/icono + + + New + Nuevo + + + Next + Sigulente + + + object + objeto + + + OK + Aceptar + + + OLE + OLE + + + OLE drag and drop + Arrastrar y colocar de OLE + + + OLE embedded object + Objeto incrustado de OLE + + + OLE linked object + Objeto vinculado de OLE + + + OLE nondefault drag and drop + Arrastrar y colocar no predeterminado de OLE + + + Open + Abrir + + + Open With + Abrir con + + + option button + botón de opción + + + option-set + opción establecida + + + package + paquete + + + Page Setup + Preparar página + + + palette window + ventana de paleta + + + pane + panel + + + parent window + ventana principal + + + password + contraseña + + + Paste + Pegar + + + Paste Link + Pegar vínculo + + + Paste Shortcut + Pegar acceso directo + + + Paste Special + Pegado especial + + + path + ruta de acceso + + + Pause + Pausa + + + pen + lápiz + + + Play + Reproducir + + + Plug and Play + Plug and Play + + + point + señalar + verb + + + point + punto + noun + + + pointer + puntero + + + pop-up menu + menú emergente + + + pop-up window + ventana emergente + + + portrait + vertical + + + press + presionar + and hold a mouse button/y mantener presionado un botón del mouse + + + press + presionar + a key/una tecla + + + primary container + contenedor primario + + + primary window + ventana principal + + + Print + Imprimir + + + printer + impresora + + + progress indicator + indicador de progreso + control + + + project + proyecto + + + Properties + Propiedades + + + property inspector + monitor de propiedades + + + property page + página de propiedades + + + property sheet + hoja de propiedades + + + property sheet control + control de la hoja de propiedades + + + Quick View + Vista rápida + + + read-only + sólo lectura + + + recognition + reconocimiento + + + Recycle Bin + Papelera de reciclaje + Icon/icono + + + Redo + Rehacer + + + region selection + selección de área + + + registry + Registro de configuraciones + + + Repeat + Repetir + + + Replace + Reemplazar + + + Restore + Restaurar + + + Restore button + botón &quot;Restaurar&quot; + + + Resume + Reanudar + + + Retry + Reintentar + + + rich-text box + cuadro de texto enriquecido + + + Run + Ejecutar + + + Save + Guardar + + + Save as + Guardar como + + + scroll + desplazar + + + scroll arrow + flecha de desplazamiento + + + scroll bar + barra de desplazamiento + + + scroll box + cuadro de desplazamiento + + + secondary window + ventana secundaria + + + select + seleccionar + + + Select All + Seleccionar todo + + + selection + selección + + + selection handle + controlador de selección + + + Send To + Enviar a + + + separator + separador + + + Settings + Configuración + + + Setup + Configurar + for a device already installed + + + Setup + Instalar + for an application + + + shortcut + acceso directo + + + shortcut button + botón de acceso directo + + + shortcut icon + icono de acceso directo + + + shortcut key + tecla de método abreviado + + + shortcut key control + control de la tecla de método abreviado + + + Show + Mostrar + + + Shutdown + Apagar el sistema + + + single selection list box + cuadro de lista de selección simple + + + Size + Tamaño + + + size grip + ajuste de tamaño + + + slider + control deslizante + + + spin box + cuadro selector + + + Split + Dividir + + + split bar + barra de división + + + split box + cuadro de división + + + Start button + botón &quot;Inicio&quot; + + + StartUp folder + carpeta Inicio + + + status bar + barra de estado + + + Stop + Detener + + + tab control + control de fichas + + + tap + puntear + + + task bar + barra de tareas + + + task-oriented Help + Ayuda relativa a la tarea + + + template + plantilla + + + text box + cuadro de texto + + + title bar + barra de título + + + title text + texto de título + + + toggle key + tecla para alternar + + + toolbar + barra de herramientas + + + tooltip + sugerencias + + + tree view control + control de visión en árbol + + + type + escribir + verb + + + type + tipo + noun + + + unavailable + no disponible + + + Undo + Deshacer + + + Uninstall + Desinstalar + + + View + menú Ver + + + visual editing + edición visual + + + well control + control de opciones gráficas + + + What's This? + ¿Qué es esto? + + + Window + menú Ventana + + + window + ventana + + + Windows Explorer + Explorador de Windows + + + wizard + asistente + + + workbook + libro + + + workbook + libro de trabajo + + + workgroup + grupo de trabajo + + + workspace + área de trabajo + + + Yes + + + diff --git a/tools/linguist/phrasebooks/swedish.qph b/tools/linguist/phrasebooks/swedish.qph new file mode 100644 index 000000000..9c44071e8 --- /dev/null +++ b/tools/linguist/phrasebooks/swedish.qph @@ -0,0 +1,1010 @@ + + + About + Om + + + access key + snabbtangent + + + accessibility + Hjälpmedel + ikonen Accessibility + + + accessibility + tillgänglighet + + + action handle + funktionshandtag + + + active + aktiv + + + active end + aktiv slutpunkt + + + active object + aktivt objekt + + + active window + aktivt fönster + + + adornment + fönsterfält + + + Always on Top + Alltid överst + + + anchor point + startpunkt + + + Apply + Verkställ + + + auto-exit + flytta automatiskt + + + auto-repeat + upprepa automatiskt + + + automatic link + automatisk länk + + + automatic scrolling + automatisk rullning + + + autoscroll + automatisk rullning + + + Back + Föregående + + + Browse + Bläddra + + + Cancel + Avbryt + + + cascading menu + undermeny + + + check box + kryssruta + + + check mark + markering + + + child window + underfönster + + + choose + välj + + + click + klicka + + + Clipboard + Urklipp + + + Close + Stäng + + + Close button + stängningsknapp + + + collapse + komprimera + outline + + + column heading + kolumnrubrik + control + + + combo box + kombinationsruta + + + command button + kommandoknapp + + + container + behållare + + + context-sensitive Help + sammanhangsberoende hjälp + + + contextual + sammanhangsberoende + + + control + kontroll + + + Copy + Kopiera + + + Copy here + Kopiera hit + + + Create Shortcut + Skapa genväg + + + Create Shortcut Here + Skapa genväg här + + + Cut + Klipp ut + + + default + standard + + + default button + standardknapp + + + Delete + Ta bort + + + desktop + skrivbord + + + destination + mål + + + dialog box + dialogruta + + + disability + oförmåga + + + disjoint selection + osammanhängande markering + + + dock + docka + + + document + dokument + + + double-click + dubbelklicka på + + + drag + dra + + + drag-and-drop + dra och släpp + + + drop-down combo box + nedrullningsbar kombinationsruta + + + drop-down list box + nedrullningsbar listruta + + + drop-down menu + nedrullningsbar meny + + + Edit + Redigera + + + ellipsis + punkter + + + embedded object + inbäddat objekt + + + Exit + Avsluta + + + expand + expandera + an outline + + + Explore + Utforska + + + extended selection + utökad markering + + + extended selection list box + listruta för utökad markering + + + File + Arkiv + menu/meny + + + file + fil + + + Find + Sök + + + Find Next + Sök nästa + + + Find What + Sök efter + + + folder + mapp + + + font + teckensnitt + + + font size + teckenstorlek + + + font style + teckenstil + + + function key + funktionstangent + + + group box + gruppruta + + + handle + handtag + + + Help + Hjälp + + + Hide + Dölj + + + hierarchical selection + hierarkisk markering + + + hold + hålla ned + + + hot spot + aktiv punkt + + + hot zone + aktiveringszon + + + icon + ikon + + + inactive + inaktiv + + + inactive window + inaktivt fönster + + + input focus + inmatningsfokus + + + Insert + Infoga-meny + + + Insert Object + Infoga objekt + + + insertion point + insättningspunkt + + + italic + kursiv + + + label + titel + + + landscape + liggande + + + link + länk + noun + + + link + länka + verb + + + Link Here + Länka hit + + + list box + listruta + + + list view + listvy + control + + + manual link + manuell länk + + + Maximize + Maximera + + + maximize button + maximeringsknapp + + + MDI + MDI + + + menu + meny + + + menu bar + menyrad + + + menu button + menyknapp + + + menu item + menyobjekt + + + menu title + menytitel + + + message box + meddelanderuta + + + Minimize + Minimera + + + minimize button + minimeringsknapp + + + mixed-value + blandvärde + + + modal + modal + + + mode + läge + + + modeless + icke-modal + + + modifier key + ändringstangent + + + mouse + mus + + + Move + Flytta + + + Move Here + Flytta hit + + + Multiple Document Interface + multiple document interface + + + multiple selection list box + listruta för multipel markering + + + My Computer + Den här datorn + icon + + + Network Neighborhood + Nätverket + icon + + + New + Ny + + + New + Nytt + + + Next + Nästa + + + object + objekt + + + OK + OK + + + OLE + OLE + + + OLE drag and drop + dra och släpp (OLE) + + + OLE embedded object + inbäddat objekt (OLE) + + + OLE linked object + länkat objekt (OLE) + + + OLE nondefault drag and drop + utökat drag och släpp (OLE) + + + Open + Öppna + + + Open With + Öppna med + + + option button + alternativknapp + + + option-set + valt alternativ + + + package + paket + + + Page Setup + Utskriftsformat + + + palette window + palettfönster + + + pane + fönsterruta + + + parent window + moderfönster + + + password + lösenord + + + Paste + Klistra in + + + Paste Link + Klistra in länk + + + Paste Shortcut + Klistra in genväg + + + Paste Special + Klistra in special + + + path + sökväg + + + Pause + Paus + + + Play + Spela upp + + + Plug and Play + Plug and Play + + + point + peka + + + pointer + pekare + + + pop-up menu + pop up-meny + + + pop-up window + pop up-fönster + + + portrait + stående + + + press + håll ned + and hold a mouse button + + + press + tryck på + a key + + + primary container + primär behållare + + + primary window + primärt fönster + + + Print + Skriv ut + + + printer + skrivare + + + progress indicator + förloppsindikator + control + + + project + projekt + + + Properties + Egenskaper + + + property inspector + egenskapsgranskare + + + property page + egenskapssida + + + property sheet + egenskapsförteckning + + + property sheet control + kontroll i egenskapsförteckning + + + Quick View + Snabbgranskning + + + read-only + skrivskydd + + + Recycle Bin + Papperskorgen + Icon + + + Redo + Gör om + + + region selection + områdesmarkering + + + registry + Registret + + + Repeat + Upprepa + + + Replace + Ersätt + + + Restore + Återställ + + + Restore button + knappen Återställ + + + Resume + Fortsätt + + + Retry + Försök igen + + + rich-text box + rich text-ruta + + + Run + Kör + + + Save + Spara + + + Save as + Spara som + + + scroll + rulla + + + scroll arrow + rullningspil + + + scroll bar + rullningslist + + + scroll box + rullningsruta + + + secondary window + sekundärt fönster + + + select + markera + + + Select All + Markera allt + + + selection + markering + + + selection handle + markeringshandtag + + + Send To + Skicka till + + + separator + avgränsare + + + Settings + Inställningar + + + Setup + installationsprogram + + + Setup + Inställningar + + + shortcut + genväg + + + shortcut button + genvägsknapp + + + shortcut icon + genvägsikon + + + shortcut key + kortkommando + + + shortcut key control + kortkommandokontroll + + + Show + Visa + + + Shutdown + Avsluta + + + single selection list box + listruta för enkel markering + + + Size + Ändra storlek + + + Size + Storlek + + + size grip + storleksgrepp + + + slider + skjutreglage + + + spin box + rotationsruta + + + Split + Dela + + + split bar + delningslist + + + split box + delningsruta + + + Start button + startknappen + + + StartUp folder + mappen Autostart + + + status bar + statusfält + + + Stop + Stanna + + + tab control + flik + + + task bar + Aktivitetsfältet + + + task-oriented Help + aktivitetsberoende hjälp + + + template + mall + + + text box + textruta + + + title bar + namnlist + + + title text + text i namnlist + + + toggle key + växlingstangent + + + toolbar + verktygsfält + + + tooltip + funktionsbeskrivning + + + tree view control + trädkontroll + + + type + typ + noun + + + type + skriva + verb + + + unavailable + ej tillgänglig + + + Undo + Ångra + + + Uninstall + Avinstallera + + + View + Visa-meny + + + visual editing + direktredigering + + + well control + grafikkontroll + + + What's This? + Förklaring + + + Window + Fönster-meny + + + window + fönster + + + Windows Explorer + Utforskaren + + + wizard + guide + + + workbook + arbetsbok + + + workgroup + arbetsgrupp + + + workspace + arbetsyta + + + Yes + Ja + + diff --git a/tools/linguist/qdoc.conf b/tools/linguist/qdoc.conf new file mode 100644 index 000000000..86e6066e4 --- /dev/null +++ b/tools/linguist/qdoc.conf @@ -0,0 +1,15 @@ +SOURCEDIRS = $QTDIR/tools/linguist/doc +DOCDIRS = $QTDIR/tools/linguist/doc +EXAMPLEDIRS = $QTDIR/tools/linguist/tutorial +OUTPUTDIR = $QTDIR/tools/linguist/doc/html +BASE = file:$QTDIR/tools/linguist/doc/html/ +COMPANY = Trolltech +PRODUCT = TQt Linguist +VERSIONSYM = QT_VERSION_STR +DEFINE = QT_QDOC QT_.*_SUPPORT _WS_.*_ +FALSE = 0 1 +INTERNAL = no +STYLE = "h3.fn,span.fn { margin-left: 1cm; text-indent: -1cm; } +a:link { color: #af4f00; text-decoration: none } +a:visited { color: #8f2f00; text-decoration: none } +body { background: #ffffff; color: black; }" diff --git a/tools/linguist/qm2ts/main.cpp b/tools/linguist/qm2ts/main.cpp new file mode 100644 index 000000000..bfc5d3673 --- /dev/null +++ b/tools/linguist/qm2ts/main.cpp @@ -0,0 +1,128 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include + +#include +#include +#include + +typedef TQValueList TML; + +static void printUsage() +{ + fprintf( stderr, "Usage:\n" + " qm2ts [ options ] qm-files\n" + "Options:\n" + " -help Display this information and exit\n" + " -verbose\n" + " Explain what is being done\n" + " -version\n" + " Display the version of qm2ts and exit\n" ); +} + +int main( int argc, char **argv ) +{ + bool verbose = FALSE; + int numQmFiles = 0; + + for ( int i = 1; i < argc; i++ ) { + if ( qstrcmp(argv[i], "-help") == 0 ) { + printUsage(); + return 0; + } else if ( qstrcmp(argv[i], "-verbose") == 0 ) { + verbose = TRUE; + continue; + } else if ( qstrcmp(argv[i], "-version") == 0 ) { + fprintf( stderr, "qm2ts version %s\n", QT_VERSION_STR ); + return 0; + } + + numQmFiles++; + TQTranslator tor( 0 ); + if ( tor.load(argv[i], ".") ) { + TQString g = argv[i]; + g.replace( TQRegExp(TQString("\\.qm$")), TQString::null ); + g += TQString( ".ts" ); + + if ( verbose ) + fprintf( stderr, "Generating '%s'...\n", g.latin1() ); + + MetaTranslator metator; + int ignored = 0; + + TML all = tor.messages(); + TML::Iterator it; + for ( it = all.begin(); it != all.end(); ++it ) { + if ( (*it).sourceText() == 0 ) { + ignored++; + } else { + TQCString context = (*it).context(); + if ( context.isEmpty() ) + context = "@default"; + metator.insert( MetaTranslatorMessage(context, + (*it).sourceText(), (*it).comment(), + (*it).translation(), FALSE, + MetaTranslatorMessage::Finished) ); + } + } + + if ( !metator.save(g) ) { + fprintf( stderr, + "qm2ts warning: For some reason, I cannot save '%s'\n", + g.latin1() ); + } else { + if ( verbose ) { + int converted = (int) metator.messages().count(); + fprintf( stderr, " %d message%s converted (%d ignored)\n", + converted, converted == 1 ? "" : "s", ignored ); + } + if ( ignored > 0 ) + fprintf( stderr, + "qm2ts warning: File '%s' is not a TQt 2.x .qm" + " file (some information is lost)\n", + argv[i] ); + } + } else { + fprintf( stderr, + "qm2ts warning: For some reason, I cannot load '%s'\n", + argv[i] ); + } + } + + if ( numQmFiles == 0 ) { + printUsage(); + return 1; + } + return 0; +} diff --git a/tools/linguist/qm2ts/qm2ts.1 b/tools/linguist/qm2ts/qm2ts.1 new file mode 100644 index 000000000..0ea20fd7c --- /dev/null +++ b/tools/linguist/qm2ts/qm2ts.1 @@ -0,0 +1,55 @@ +.TH qm2ts 1 "18 October 2001" "Trolltech AS" \" -*- nroff -*- +.\" +.\" Copyright (C) 2001-2008 Trolltech ASA. All rights reserved. +.\" +.\" This file is part of Qt and may be distributed and used according to +.\" the terms and conditions described in the LICENSE file. +.\" +.SH NAME +qm2ts \- generate Qt Linguist translation files from Qt 2.x message files +.SH SYNOPSIS +.B qm2ts +.RI "[ " options " ] " qm-files +.SH DESCRIPTION +This page documents the +.B Qt Linguist Qm2ts +tool for the Qt GUI toolkit. +.B Qm2ts +converts Qt 2.x message files (.qm files) into source message files +(.ts files). +.PP +The .ts file format is a simple human-readable XML format that can be +used with version control systems if retquired. It is understood by +.B lupdate, +.B lrelease +and +.B Qt Linguist. +.PP +.B qm2ts +is provided to ease porting from the old internationalization +tools +.B (findtr, +.B mergetr +and +.B msg2qm) +to the new ones. It will not accept Qt message files generated by +.B lrelease, +as +.B lrelease +compresses .qm files by stripping unnecessary information for lookup. +.SH OPTIONS +.TP +.I "-help" +Display the usage and exit. +.TP +.I "-verbose" +Explain what is being done. +.TP +.I "-version" +Display the version of +.B qm2ts +and exit. +.SH "SEE ALSO" +.BR http://doc.trolltech.com/i18n.html +.SH AUTHOR +Jasmin Blanchette, Trolltech ASA diff --git a/tools/linguist/qm2ts/qm2ts.pro b/tools/linguist/qm2ts/qm2ts.pro new file mode 100644 index 000000000..3868e30c2 --- /dev/null +++ b/tools/linguist/qm2ts/qm2ts.pro @@ -0,0 +1,15 @@ +TEMPLATE = app +CONFIG += qt warn_on console +HEADERS = ../shared/metatranslator.h +SOURCES = main.cpp \ + ../shared/metatranslator.cpp + +DEFINES += QT_INTERNAL_XML +include( ../../../src/qt_professional.pri ) + +TARGET = qm2ts +INCLUDEPATH += ../shared +DESTDIR = ../../../bin + +target.path=$$bins.path +INSTALLS += target diff --git a/tools/linguist/shared/metatranslator.cpp b/tools/linguist/shared/metatranslator.cpp new file mode 100644 index 000000000..2e02f1c08 --- /dev/null +++ b/tools/linguist/shared/metatranslator.cpp @@ -0,0 +1,601 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "metatranslator.h" + +#include +#include +#include +#include +#include +#include +#include + +static bool encodingIsUtf8( const TQXmlAttributes& atts ) +{ + for ( int i = 0; i < atts.length(); i++ ) { + // utf8="true" is a pre-3.0 syntax + if ( atts.qName(i) == TQString("utf8") ) { + return ( atts.value(i) == TQString("true") ); + } else if ( atts.qName(i) == TQString("encoding") ) { + return ( atts.value(i) == TQString("UTF-8") ); + } + } + return FALSE; +} + +class TsHandler : public TQXmlDefaultHandler +{ +public: + TsHandler( MetaTranslator *translator ) + : tor( translator ), type( MetaTranslatorMessage::Finished ), + inMessage( FALSE ), ferrorCount( 0 ), contextIsUtf8( FALSE ), + messageIsUtf8( FALSE ) { } + + virtual bool startElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName, + const TQXmlAttributes& atts ); + virtual bool endElement( const TQString& namespaceURI, + const TQString& localName, const TQString& qName ); + virtual bool characters( const TQString& ch ); + virtual bool fatalError( const TQXmlParseException& exception ); + +private: + MetaTranslator *tor; + MetaTranslatorMessage::Type type; + bool inMessage; + TQString context; + TQString source; + TQString comment; + TQString translation; + + TQString accum; + int ferrorCount; + bool contextIsUtf8; + bool messageIsUtf8; +}; + +bool TsHandler::startElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName, + const TQXmlAttributes& atts ) +{ + if ( qName == TQString("byte") ) { + for ( int i = 0; i < atts.length(); i++ ) { + if ( atts.qName(i) == TQString("value") ) { + TQString value = atts.value( i ); + int base = 10; + if ( value.startsWith("x") ) { + base = 16; + value = value.mid( 1 ); + } + int n = value.toUInt( 0, base ); + if ( n != 0 ) + accum += TQChar( n ); + } + } + } else { + if ( qName == TQString("context") ) { + context.truncate( 0 ); + source.truncate( 0 ); + comment.truncate( 0 ); + translation.truncate( 0 ); + contextIsUtf8 = encodingIsUtf8( atts ); + } else if ( qName == TQString("message") ) { + inMessage = TRUE; + type = MetaTranslatorMessage::Finished; + source.truncate( 0 ); + comment.truncate( 0 ); + translation.truncate( 0 ); + messageIsUtf8 = encodingIsUtf8( atts ); + } else if ( qName == TQString("translation") ) { + for ( int i = 0; i < atts.length(); i++ ) { + if ( atts.qName(i) == TQString("type") ) { + if ( atts.value(i) == TQString("unfinished") ) + type = MetaTranslatorMessage::Unfinished; + else if ( atts.value(i) == TQString("obsolete") ) + type = MetaTranslatorMessage::Obsolete; + else + type = MetaTranslatorMessage::Finished; + } + } + } + accum.truncate( 0 ); + } + return TRUE; +} + +bool TsHandler::endElement( const TQString& /* namespaceURI */, + const TQString& /* localName */, + const TQString& qName ) +{ + if ( qName == TQString("codec") || qName == TQString("defaultcodec") ) { + // "codec" is a pre-3.0 syntax + tor->setCodec( accum ); + } else if ( qName == TQString("name") ) { + context = accum; + } else if ( qName == TQString("source") ) { + source = accum; + } else if ( qName == TQString("comment") ) { + if ( inMessage ) { + comment = accum; + } else { + if ( contextIsUtf8 ) + tor->insert( MetaTranslatorMessage(context.utf8(), + ContextComment, + accum.utf8(), TQString::null, TRUE, + MetaTranslatorMessage::Unfinished) ); + else + tor->insert( MetaTranslatorMessage(context.ascii(), + ContextComment, + accum.ascii(), TQString::null, FALSE, + MetaTranslatorMessage::Unfinished) ); + } + } else if ( qName == TQString("translation") ) { + translation = accum; + } else if ( qName == TQString("message") ) { + if ( messageIsUtf8 ) + tor->insert( MetaTranslatorMessage(context.utf8(), source.utf8(), + comment.utf8(), translation, + TRUE, type) ); + else + tor->insert( MetaTranslatorMessage(context.ascii(), source.ascii(), + comment.ascii(), translation, + FALSE, type) ); + inMessage = FALSE; + } + return TRUE; +} + +bool TsHandler::characters( const TQString& ch ) +{ + TQString t = ch; + t.replace( "\r", "" ); + accum += t; + return TRUE; +} + +bool TsHandler::fatalError( const TQXmlParseException& exception ) +{ + if ( ferrorCount++ == 0 ) { + TQString msg; + msg.sprintf( "Parse error at line %d, column %d (%s).", + exception.lineNumber(), exception.columnNumber(), + exception.message().latin1() ); + if ( qApp == 0 ) + fprintf( stderr, "XML error: %s\n", msg.latin1() ); + else + TQMessageBox::information( qApp->mainWidget(), + TQObject::tr("TQt Linguist"), msg ); + } + return FALSE; +} + +static TQString numericEntity( int ch ) +{ + return TQString( ch <= 0x20 ? "" : "&#x%1;" ) + .arg( ch, 0, 16 ); +} + +static TQString protect( const TQCString& str ) +{ + TQString result; + int len = (int) str.length(); + for ( int k = 0; k < len; k++ ) { + switch( str[k] ) { + case '\"': + result += TQString( """ ); + break; + case '&': + result += TQString( "&" ); + break; + case '>': + result += TQString( ">" ); + break; + case '<': + result += TQString( "<" ); + break; + case '\'': + result += TQString( "'" ); + break; + default: + if ( (uchar) str[k] < 0x20 && str[k] != '\n' ) + result += numericEntity( (uchar) str[k] ); + else + result += str[k]; + } + } + return result; +} + +static TQString evilBytes( const TQCString& str, bool utf8 ) +{ + if ( utf8 ) { + return protect( str ); + } else { + TQString result; + TQCString t = protect( str ).latin1(); + int len = (int) t.length(); + for ( int k = 0; k < len; k++ ) { + if ( (uchar) t[k] >= 0x7f ) + result += numericEntity( (uchar) t[k] ); + else + result += TQChar( t[k] ); + } + return result; + } +} + +MetaTranslatorMessage::MetaTranslatorMessage() + : utfeight( FALSE ), ty( Unfinished ) +{ +} + +MetaTranslatorMessage::MetaTranslatorMessage( const char *context, + const char *sourceText, + const char *comment, + const TQString& translation, + bool utf8, Type type ) + : TQTranslatorMessage( context, sourceText, comment, translation ), + utfeight( FALSE ), ty( type ) +{ + /* + Don't use UTF-8 if it makes no difference. UTF-8 should be + reserved for the real problematic case: non-ASCII (possibly + non-Latin-1) characters in .ui files. + */ + if ( utf8 ) { + if ( sourceText != 0 ) { + int i = 0; + while ( sourceText[i] != '\0' ) { + if ( (uchar) sourceText[i] >= 0x80 ) { + utfeight = TRUE; + break; + } + i++; + } + } + if ( !utfeight && comment != 0 ) { + int i = 0; + while ( comment[i] != '\0' ) { + if ( (uchar) comment[i] >= 0x80 ) { + utfeight = TRUE; + break; + } + i++; + } + } + } +} + +MetaTranslatorMessage::MetaTranslatorMessage( const MetaTranslatorMessage& m ) + : TQTranslatorMessage( m ), utfeight( m.utfeight ), ty( m.ty ) +{ +} + +MetaTranslatorMessage& MetaTranslatorMessage::operator=( + const MetaTranslatorMessage& m ) +{ + TQTranslatorMessage::operator=( m ); + utfeight = m.utfeight; + ty = m.ty; + return *this; +} + +bool MetaTranslatorMessage::operator==( const MetaTranslatorMessage& m ) const +{ + return qstrcmp( context(), m.context() ) == 0 && + qstrcmp( sourceText(), m.sourceText() ) == 0 && + qstrcmp( comment(), m.comment() ) == 0; +} + +bool MetaTranslatorMessage::operator<( const MetaTranslatorMessage& m ) const +{ + int delta = qstrcmp( context(), m.context() ); + if ( delta == 0 ) + delta = qstrcmp( sourceText(), m.sourceText() ); + if ( delta == 0 ) + delta = qstrcmp( comment(), m.comment() ); + return delta < 0; +} + +MetaTranslator::MetaTranslator() +{ + clear(); +} + +MetaTranslator::MetaTranslator( const MetaTranslator& tor ) + : mm( tor.mm ), codecName( tor.codecName ), codec( tor.codec ) +{ +} + +MetaTranslator& MetaTranslator::operator=( const MetaTranslator& tor ) +{ + mm = tor.mm; + codecName = tor.codecName; + codec = tor.codec; + return *this; +} + +void MetaTranslator::clear() +{ + mm.clear(); + codecName = "ISO-8859-1"; + codec = 0; +} + +bool MetaTranslator::load( const TQString& filename ) +{ + TQFile f( filename ); + if ( !f.open(IO_ReadOnly) ) + return FALSE; + + TQTextStream t( &f ); + TQXmlInputSource in( t ); + TQXmlSimpleReader reader; + reader.setFeature( "http://xml.org/sax/features/namespaces", FALSE ); + reader.setFeature( "http://xml.org/sax/features/namespace-prefixes", TRUE ); + TQXmlDefaultHandler *hand = new TsHandler( this ); + reader.setContentHandler( hand ); + reader.setErrorHandler( hand ); + + bool ok = reader.parse( in ); + reader.setContentHandler( 0 ); + reader.setErrorHandler( 0 ); + delete hand; + f.close(); + return ok; +} + +bool MetaTranslator::save( const TQString& filename ) const +{ + TQFile f( filename ); + if ( !f.open(IO_WriteOnly) ) + return FALSE; + + TQTextStream t( &f ); + t.setCodec( TQTextCodec::codecForName("ISO-8859-1") ); + + t << "\n"; + if ( codecName != "ISO-8859-1" ) + t << "" << codecName << "\n"; + TMM::ConstIterator m = mm.begin(); + while ( m != mm.end() ) { + TMMInv inv; + TMMInv::Iterator i; + bool contextIsUtf8 = m.key().utf8(); + TQCString context = m.key().context(); + TQCString comment = ""; + + do { + if ( TQCString(m.key().sourceText()) == ContextComment ) { + if ( m.key().type() != MetaTranslatorMessage::Obsolete ) { + contextIsUtf8 = m.key().utf8(); + comment = TQCString( m.key().comment() ); + } + } else { + inv.insert( *m, m.key() ); + } + } while ( ++m != mm.end() && TQCString(m.key().context()) == context ); + + t << "\n"; + t << " " << evilBytes( context, contextIsUtf8 ) + << "\n"; + if ( !comment.isEmpty() ) + t << " " << evilBytes( comment, contextIsUtf8 ) + << "\n"; + + for ( i = inv.begin(); i != inv.end(); ++i ) { + // no need for such noise + if ( (*i).type() == MetaTranslatorMessage::Obsolete && + (*i).translation().isEmpty() ) + continue; + + t << " \n" + << " " << evilBytes( (*i).sourceText(), + (*i).utf8() ) + << "\n"; + if ( !TQCString((*i).comment()).isEmpty() ) + t << " " << evilBytes( (*i).comment(), + (*i).utf8() ) + << "\n"; + t << " " << protect( (*i).translation().utf8() ) + << "\n"; + t << " \n"; + } + t << "\n"; + } + t << "\n"; + f.close(); + return TRUE; +} + +bool MetaTranslator::release( const TQString& filename, bool verbose, + TQTranslator::SaveMode mode ) const +{ + TQTranslator tor( 0 ); + int finished = 0; + int unfinished = 0; + int untranslated = 0; + TMM::ConstIterator m; + + for ( m = mm.begin(); m != mm.end(); ++m ) { + if ( m.key().type() != MetaTranslatorMessage::Obsolete ) { + if ( m.key().translation().isEmpty() ) { + untranslated++; + } else { + if ( m.key().type() == MetaTranslatorMessage::Unfinished ) + unfinished++; + else + finished++; + + TQCString context = m.key().context(); + TQCString sourceText = m.key().sourceText(); + TQCString comment = m.key().comment(); + TQString translation = m.key().translation(); + + /* + Drop the comment in (context, sourceText, comment), + unless (context, sourceText, "") already exists, or + unless we already dropped the comment of (context, + sourceText, comment0). + */ + if ( comment.isEmpty() + || contains(context, sourceText, "") + || !tor.findMessage(context, sourceText, "").translation() + .isNull() ) { + tor.insert( m.key() ); + } else { + tor.insert( TQTranslatorMessage(context, sourceText, "", + translation) ); + } + } + } + } + + bool saved = tor.save( filename, mode ); + if ( saved && verbose ) + fprintf( stderr, + " %d finished, %d unfinished and %d untranslated messages\n", + finished, unfinished, untranslated ); + + return saved; +} + +bool MetaTranslator::contains( const char *context, const char *sourceText, + const char *comment ) const +{ + return mm.find( MetaTranslatorMessage(context, sourceText, comment) ) != + mm.end(); +} + +void MetaTranslator::insert( const MetaTranslatorMessage& m ) +{ + int pos = (int)mm.count(); + TMM::Iterator n = mm.find( m ); + if ( n != mm.end() ) + pos = *n; + mm.replace( m, pos ); +} + +void MetaTranslator::stripObsoleteMessages() +{ + TMM newmm; + + TMM::Iterator m = mm.begin(); + while ( m != mm.end() ) { + if ( m.key().type() != MetaTranslatorMessage::Obsolete ) + newmm.insert( m.key(), *m ); + ++m; + } + mm = newmm; +} + +void MetaTranslator::stripEmptyContexts() +{ + TMM newmm; + + TMM::Iterator m = mm.begin(); + while ( m != mm.end() ) { + if ( TQCString(m.key().sourceText()) == ContextComment ) { + TMM::Iterator n = m; + ++n; + // the context comment is followed by other messages + if ( n != newmm.end() && + qstrcmp(m.key().context(), n.key().context()) == 0 ) + newmm.insert( m.key(), *m ); + } else { + newmm.insert( m.key(), *m ); + } + ++m; + } + mm = newmm; +} + +void MetaTranslator::setCodec( const char *name ) +{ + const int latin1 = 4; + + codecName = name; + codec = TQTextCodec::codecForName( name ); + if ( codec == 0 || codec->mibEnum() == latin1 ) + codec = 0; +} + +TQString MetaTranslator::toUnicode( const char *str, bool utf8 ) const +{ + if ( utf8 ) + return TQString::fromUtf8( str ); + else if ( codec == 0 ) + return TQString( str ); + else + return codec->toUnicode( str ); +} + +TQValueList MetaTranslator::messages() const +{ + int n = (int)mm.count(); + TMM::ConstIterator *t = new TMM::ConstIterator[n + 1]; + TMM::ConstIterator m; + for ( m = mm.begin(); m != mm.end(); ++m ) + t[*m] = m; + + TQValueList val; + for ( int i = 0; i < n; i++ ) + val.append( t[i].key() ); + + delete[] t; + return val; +} + +TQValueList MetaTranslator::translatedMessages() const +{ + TQValueList val; + TMM::ConstIterator m; + for ( m = mm.begin(); m != mm.end(); ++m ) { + if ( m.key().type() == MetaTranslatorMessage::Finished ) + val.append( m.key() ); + } + return val; +} diff --git a/tools/linguist/shared/metatranslator.h b/tools/linguist/shared/metatranslator.h new file mode 100644 index 000000000..e4e3199d4 --- /dev/null +++ b/tools/linguist/shared/metatranslator.h @@ -0,0 +1,120 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef METATRANSLATOR_H +#define METATRANSLATOR_H + +#include +#include +#include +#include + +class TQTextCodec; + +class MetaTranslatorMessage : public TQTranslatorMessage +{ +public: + enum Type { Unfinished, Finished, Obsolete }; + + MetaTranslatorMessage(); + MetaTranslatorMessage( const char *context, const char *sourceText, + const char *comment, + const TQString& translation = TQString::null, + bool utf8 = FALSE, Type type = Unfinished ); + MetaTranslatorMessage( const MetaTranslatorMessage& m ); + + MetaTranslatorMessage& operator=( const MetaTranslatorMessage& m ); + + void setType( Type nt ) { ty = nt; } + Type type() const { return ty; } + bool utf8() const { return utfeight; } + + bool operator==( const MetaTranslatorMessage& m ) const; + bool operator!=( const MetaTranslatorMessage& m ) const + { return !operator==( m ); } + bool operator<( const MetaTranslatorMessage& m ) const; + bool operator<=( const MetaTranslatorMessage& m ) + { return !operator>( m ); } + bool operator>( const MetaTranslatorMessage& m ) const + { return this->operator<( m ); } + bool operator>=( const MetaTranslatorMessage& m ) const + { return !operator<( m ); } + +private: + bool utfeight; + Type ty; +}; + +class MetaTranslator +{ +public: + MetaTranslator(); + MetaTranslator( const MetaTranslator& tor ); + + MetaTranslator& operator=( const MetaTranslator& tor ); + + void clear(); + bool load( const TQString& filename ); + bool save( const TQString& filename ) const; + bool release( const TQString& filename, bool verbose = FALSE, + TQTranslator::SaveMode mode = TQTranslator::Stripped ) const; + + bool contains( const char *context, const char *sourceText, + const char *comment ) const; + void insert( const MetaTranslatorMessage& m ); + + void stripObsoleteMessages(); + void stripEmptyContexts(); + + void setCodec( const char *name ); + TQString toUnicode( const char *str, bool utf8 ) const; + + TQValueList messages() const; + TQValueList translatedMessages() const; + +private: + typedef TQMap TMM; + typedef TQMap TMMInv; + + TMM mm; + TQCString codecName; + TQTextCodec *codec; +}; + +/* + This is a tquick hack. The proper way to handle this would be + to extend MetaTranslator's interface. +*/ +#define ContextComment "QT_LINGUIST_INTERNAL_CONTEXT_COMMENT" + +#endif diff --git a/tools/linguist/shared/proparser.cpp b/tools/linguist/shared/proparser.cpp new file mode 100644 index 000000000..ded46b5c1 --- /dev/null +++ b/tools/linguist/shared/proparser.cpp @@ -0,0 +1,217 @@ +/********************************************************************** +** Copyright (C) 2000-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#include "proparser.h" + +#include +#include +#include +#include +#include +#include + +#ifdef Q_OS_UNIX +#include +#endif + +#ifdef Q_OS_WIN32 +#define QT_POPEN _popen +#else +#define QT_POPEN popen +#endif + +TQString loadFile( const TQString &fileName ) +{ + TQFile file( fileName ); + if ( !file.open(IO_ReadOnly) ) { + fprintf( stderr, "error: Cannot load '%s': %s\n", + file.name().latin1(), + file.errorString().latin1() ); + return TQString(); + } + + TQTextStream in( &file ); + return in.read(); +} + +TQMap proFileTagMap( const TQString& text ) +{ + TQString t = text; + TQMap tagMap; + bool stillProcess = true; // If include() has a $$tag then we need to reprocess + + while(stillProcess) { + + /* + Strip any commments before we try to include. We + still need to do it after we include to make sure the + included file does not have comments + */ + t.replace( TQRegExp(TQString("#[^\n]*\n")), TQString(" ") ); + + /* + Process include() commands. + $$PWD is a special case so we have to change it while + we know where the included file is. + */ + TQRegExp callToInclude("include\\s*\\(\\s*([^()\\s]+)\\s*\\)"); + int i = 0; + while ( (i = callToInclude.search(t, i)) != -1 ) { + bool doneWithVar = false; + TQString fileName = callToInclude.cap(1); + TQString after = fileName.replace("$$PWD", TQDir::currentDirPath()); + if (!tagMap.isEmpty() && after.contains("$$")) { + TQRegExp var( "\\$\\$[({]?([a-zA-Z0-9_]+)[)}]?" ); + int ii = 0; + while ((ii = after.find(var, ii)) != -1) { + if (tagMap.contains(var.cap(1))) { + after.replace(ii, var.cap(0).length(), tagMap[var.cap(1)]); + } else { // Couldn't find it + doneWithVar = true; + break; + } + } + + } + if (doneWithVar || !after.contains("$$")) { + after = loadFile(after); + TQFileInfo fi(callToInclude.cap(1)); + after.replace("$$PWD", fi.dirPath()); + t.replace( i, callToInclude.matchedLength(), after ); + } + i += after.length(); + } + + /* + Strip comments, merge lines ending with backslash, add + spaces around '=' and '+=', replace '\n' with ';', and + simplify white spaces. + */ + t.replace( TQRegExp(TQString("#[^\n]*\n")), TQString(" ") ); + t.replace( TQRegExp(TQString("\\\\[^\n\\S]*\n")), TQString(" ") ); + t.replace( "=", TQString(" = ") ); + t.replace( "+ =", TQString(" += ") ); + t.replace( "\n", TQString(";") ); + t = t.simplifyWhiteSpace(); + + /* + Populate tagMap with 'key = value' entries. + */ + TQStringList lines = TQStringList::split( TQChar(';'), t ); + TQStringList::Iterator line; + for ( line = lines.begin(); line != lines.end(); ++line ) { + TQStringList toks = TQStringList::split( TQChar(' '), *line ); + + if ( toks.count() >= 3 && + (toks[1] == TQString("=") || toks[1] == TQString("+=")) ) { + TQString tag = toks.first(); + int k = tag.findRev( TQChar(':') ); // as in 'unix:' + if ( k != -1 ) + tag = tag.mid( k + 1 ); + toks.remove( toks.begin() ); + + TQString action = toks.first(); + toks.remove( toks.begin() ); + + if ( tagMap.contains(tag) ) { + if ( action == TQString("=") ) + tagMap.replace( tag, toks.join(TQChar(' ')) ); + else + tagMap[tag] += TQChar( ' ' ) + toks.join( TQChar(' ') ); + } else { + tagMap[tag] = toks.join( TQChar(' ') ); + } + } + } + + /* + Expand $$variables within the 'value' part of a 'key = value' + pair. + */ + TQRegExp var( "\\$\\$[({]?([a-zA-Z0-9_]+)[)}]?" ); + TQMap::Iterator it; + for ( it = tagMap.begin(); it != tagMap.end(); ++it ) { + int i = 0; + while ( (i = var.search((*it), i)) != -1 ) { + int len = var.matchedLength(); + TQString invocation = var.cap(1); + TQString after; + + if ( invocation == "system" ) { + // skip system(); it will be handled in the next pass + ++i; + } else { + if ( tagMap.contains(invocation) ) + after = tagMap[invocation]; + else if (invocation.lower() == "pwd") + after = TQDir::currentDirPath(); + (*it).replace( i, len, after ); + i += after.length(); + } + } + } + + /* + Execute system() calls. + */ + TQRegExp callToSystem( "\\$\\$system\\s*\\(([^()]*)\\)" ); + for ( it = tagMap.begin(); it != tagMap.end(); ++it ) { + int i = 0; + while ( (i = callToSystem.search((*it), i)) != -1 ) { + /* + This code is stolen from qmake's project.cpp file. + Ideally we would use the same parser, so we wouldn't + have this code duplication. + */ + TQString after; + char buff[256]; + FILE *proc = QT_POPEN( callToSystem.cap(1).latin1(), "r" ); + while ( proc && !feof(proc) ) { + int read_in = (int)fread( buff, 1, 255, proc ); + if ( !read_in ) + break; + for ( int i = 0; i < read_in; i++ ) { + if ( buff[i] == '\n' || buff[i] == '\t' ) + buff[i] = ' '; + } + buff[read_in] = '\0'; + after += buff; + } + (*it).replace( i, callToSystem.matchedLength(), after ); + i += after.length(); + } + } + stillProcess = callToInclude.search(t) != -1; + } + return tagMap; +} diff --git a/tools/linguist/shared/proparser.h b/tools/linguist/shared/proparser.h new file mode 100644 index 000000000..8899443be --- /dev/null +++ b/tools/linguist/shared/proparser.h @@ -0,0 +1,42 @@ +/********************************************************************** +** Copyright (C) 2005-2008 Trolltech ASA. All rights reserved. +** +** This file is part of TQt Linguist. +** +** This file may be used under the terms of the GNU General +** Public License versions 2.0 or 3.0 as published by the Free +** Software Foundation and appearing in the files LICENSE.GPL2 +** and LICENSE.GPL3 included in the packaging of this file. +** Alternatively you may (at your option) use any later version +** of the GNU General Public License if such license has been +** publicly approved by Trolltech ASA (or its successors, if any) +** and the KDE Free TQt Foundation. +** +** Please review the following information to ensure GNU General +** Public Licensing retquirements will be met: +** http://trolltech.com/products/qt/licenses/licensing/opensource/. +** If you are unsure which license is appropriate for your use, please +** review the following information: +** http://trolltech.com/products/qt/licenses/licensing/licensingoverview +** or contact the sales department at sales@trolltech.com. +** +** Licensees holding valid TQt Commercial licenses may use this file in +** accordance with the TQt Commercial License Agreement provided with +** the Software. +** +** This file is provided "AS IS" with NO WARRANTY OF ANY KIND, +** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE. Trolltech reserves all rights not granted +** herein. +** +**********************************************************************/ + +#ifndef PROPARSER_H +#define PROPARSER_H + +#include +#include + +TQMap proFileTagMap( const TQString& text ); + +#endif diff --git a/tools/linguist/tutorial/tt1/main.cpp b/tools/linguist/tutorial/tt1/main.cpp new file mode 100644 index 000000000..2cee6e11e --- /dev/null +++ b/tools/linguist/tutorial/tt1/main.cpp @@ -0,0 +1,25 @@ +/**************************************************************** +** +** Translation tutorial 1 +** +****************************************************************/ + +#include +#include +#include + + +int main( int argc, char **argv ) +{ + TQApplication app( argc, argv ); + + TQTranslator translator( 0 ); + translator.load( "tt1_la", "." ); + app.installTranslator( &translator ); + + TQPushButton hello( TQPushButton::tr("Hello world!"), 0 ); + + app.setMainWidget( &hello ); + hello.show(); + return app.exec(); +} diff --git a/tools/linguist/tutorial/tt1/tt1.pro b/tools/linguist/tutorial/tt1/tt1.pro new file mode 100644 index 000000000..3b5249cbc --- /dev/null +++ b/tools/linguist/tutorial/tt1/tt1.pro @@ -0,0 +1,4 @@ +TEMPLATE = app +CONFIG += qt warn_on +SOURCES = main.cpp +TRANSLATIONS = tt1_la.ts diff --git a/tools/linguist/tutorial/tt2/arrowpad.cpp b/tools/linguist/tutorial/tt2/arrowpad.cpp new file mode 100644 index 000000000..8e23d931d --- /dev/null +++ b/tools/linguist/tutorial/tt2/arrowpad.cpp @@ -0,0 +1,31 @@ +/**************************************************************** +** +** Implementation of ArrowPad class, translation tutorial 2 +** +****************************************************************/ + +#include "arrowpad.h" + +#include + +ArrowPad::ArrowPad( TQWidget *parent, const char *name ) + : TQGrid( 3, Horizontal, parent, name ) +{ + setMargin( 10 ); + setSpacing( 10 ); + + skip(); + (void) new TQPushButton( tr("&Up"), this ); + skip(); + (void) new TQPushButton( tr("&Left"), this ); + skip(); + (void) new TQPushButton( tr("&Right"), this ); + skip(); + (void) new TQPushButton( tr("&Down"), this ); + skip(); +} + +void ArrowPad::skip() +{ + (void) new TQWidget( this ); +} diff --git a/tools/linguist/tutorial/tt2/arrowpad.h b/tools/linguist/tutorial/tt2/arrowpad.h new file mode 100644 index 000000000..06e11fa45 --- /dev/null +++ b/tools/linguist/tutorial/tt2/arrowpad.h @@ -0,0 +1,22 @@ +/**************************************************************** +** +** Definition of ArrowPad class, translation tutorial 2 +** +****************************************************************/ + +#ifndef ARROWPAD_H +#define ARROWPAD_H + +#include + +class ArrowPad : public TQGrid +{ + Q_OBJECT +public: + ArrowPad( TQWidget *parent = 0, const char *name = 0 ); + +private: + void skip(); +}; + +#endif diff --git a/tools/linguist/tutorial/tt2/main.cpp b/tools/linguist/tutorial/tt2/main.cpp new file mode 100644 index 000000000..132d4c49f --- /dev/null +++ b/tools/linguist/tutorial/tt2/main.cpp @@ -0,0 +1,26 @@ +/**************************************************************** +** +** Translation tutorial 2 +** +****************************************************************/ + +#include "mainwindow.h" + +#include +#include +#include +#include + +int main( int argc, char **argv ) +{ + TQApplication app( argc, argv ); + + TQTranslator translator( 0 ); + translator.load( TQString("tt2_") + TQTextCodec::locale(), "." ); + app.installTranslator( &translator ); + + MainWindow *mw = new MainWindow; + app.setMainWidget( mw ); + mw->show(); + return app.exec(); +} diff --git a/tools/linguist/tutorial/tt2/mainwindow.cpp b/tools/linguist/tutorial/tt2/mainwindow.cpp new file mode 100644 index 000000000..542846b49 --- /dev/null +++ b/tools/linguist/tutorial/tt2/mainwindow.cpp @@ -0,0 +1,26 @@ +/**************************************************************** +** +** Implementation of MainWindow class, translation tutorial 2 +** +****************************************************************/ + +#include "arrowpad.h" +#include "mainwindow.h" + +#include +#include +#include +#include + +MainWindow::MainWindow( TQWidget *parent, const char *name ) + : TQMainWindow( parent, name ) +{ + ArrowPad *ap = new ArrowPad( this, "arrow pad" ); + setCentralWidget( ap ); + + TQPopupMenu *file = new TQPopupMenu( this ); + file->insertItem( tr("E&xit"), qApp, SLOT(tquit()), + tr("Ctrl+Q", "Quit") ); + menuBar()->insertItem( tr("&File"), file ); + menuBar()->setSeparator( TQMenuBar::InWindowsStyle ); +} diff --git a/tools/linguist/tutorial/tt2/mainwindow.h b/tools/linguist/tutorial/tt2/mainwindow.h new file mode 100644 index 000000000..0d023bb6b --- /dev/null +++ b/tools/linguist/tutorial/tt2/mainwindow.h @@ -0,0 +1,19 @@ +/**************************************************************** +** +** Definition of MainWindow class, translation tutorial 2 +** +****************************************************************/ + +#ifndef MAINWINDOW_H +#define MAINWINDOW_H + +#include + +class MainWindow : public TQMainWindow +{ + Q_OBJECT +public: + MainWindow( TQWidget *parent = 0, const char *name = 0 ); +}; + +#endif diff --git a/tools/linguist/tutorial/tt2/tt2.pro b/tools/linguist/tutorial/tt2/tt2.pro new file mode 100644 index 000000000..8c1ea6d4c --- /dev/null +++ b/tools/linguist/tutorial/tt2/tt2.pro @@ -0,0 +1,9 @@ +TEMPLATE = app +CONFIG += qt warn_on +HEADERS = arrowpad.h \ + mainwindow.h +SOURCES = arrowpad.cpp \ + main.cpp \ + mainwindow.cpp +TRANSLATIONS = tt2_fr.ts \ + tt2_nl.ts diff --git a/tools/linguist/tutorial/tt3/main.cpp b/tools/linguist/tutorial/tt3/main.cpp new file mode 100644 index 000000000..0c2f083c6 --- /dev/null +++ b/tools/linguist/tutorial/tt3/main.cpp @@ -0,0 +1,26 @@ +/**************************************************************** +** +** Translation tutorial 3 +** +****************************************************************/ + +#include "mainwindow.h" + +#include +#include +#include +#include + +int main( int argc, char **argv ) +{ + TQApplication app( argc, argv ); + + TQTranslator translator( 0 ); + translator.load( TQString("tt3_") + TQTextCodec::locale(), "." ); + app.installTranslator( &translator ); + + MainWindow *mw = new MainWindow; + app.setMainWidget( mw ); + mw->show(); + return app.exec(); +} diff --git a/tools/linguist/tutorial/tt3/mainwindow.cpp b/tools/linguist/tutorial/tt3/mainwindow.cpp new file mode 100644 index 000000000..a0aca2b9e --- /dev/null +++ b/tools/linguist/tutorial/tt3/mainwindow.cpp @@ -0,0 +1,47 @@ +/**************************************************************** +** +** Implementation of MainWindow class, translation tutorial 3 +** +****************************************************************/ + +#include "mainwindow.h" +#include "printpanel.h" + +#include +#include +#include +#include +#include + +MainWindow::MainWindow( TQWidget *parent, const char *name ) + : TQMainWindow( parent, name ) +{ + setCaption( tr("Troll Print 1.0") ); + + PrintPanel *pp = new PrintPanel( this ); + setCentralWidget( pp ); + + TQPopupMenu *file = new TQPopupMenu( this ); + file->insertItem( tr("E&xit"), qApp, SLOT(tquit()), + tr("Ctrl+Q", "Quit") ); + TQPopupMenu *help = new TQPopupMenu( this ); + help->insertItem( tr("&About"), this, SLOT(about()), Key_F1 ); + help->insertItem( tr("About &TQt"), this, SLOT(aboutTQt()) ); + + menuBar()->insertItem( tr("&File"), file ); + menuBar()->insertSeparator(); + menuBar()->insertItem( tr("&Help"), help ); + menuBar()->setSeparator( TQMenuBar::InWindowsStyle ); +} + +void MainWindow::about() +{ + TQMessageBox::information( this, tr("About Troll Print 1.0"), + tr("Troll Print 1.0.\n\n" + "Copyright 1999 Macroshaft, Inc.") ); +} + +void MainWindow::aboutTQt() +{ + TQMessageBox::aboutTQt( this ); +} diff --git a/tools/linguist/tutorial/tt3/mainwindow.h b/tools/linguist/tutorial/tt3/mainwindow.h new file mode 100644 index 000000000..dc9ad11e1 --- /dev/null +++ b/tools/linguist/tutorial/tt3/mainwindow.h @@ -0,0 +1,23 @@ +/**************************************************************** +** +** Definition of MainWindow class, translation tutorial 3 +** +****************************************************************/ + +#ifndef MAINWINDOW_H +#define MAINWINDOW_H + +#include + +class MainWindow : public TQMainWindow +{ + Q_OBJECT +public: + MainWindow( TQWidget *parent = 0, const char *name = 0 ); + +private slots: + void about(); + void aboutTQt(); +}; + +#endif diff --git a/tools/linguist/tutorial/tt3/printpanel.cpp b/tools/linguist/tutorial/tt3/printpanel.cpp new file mode 100644 index 000000000..c377efc26 --- /dev/null +++ b/tools/linguist/tutorial/tt3/printpanel.cpp @@ -0,0 +1,37 @@ +/**************************************************************** +** +** Implementation of PrintPanel class, translation tutorial 3 +** +****************************************************************/ + +#include "printpanel.h" + +#include +#include +#include + +PrintPanel::PrintPanel( TQWidget *parent, const char *name ) + : TQVBox( parent, name ) +{ + setMargin( 10 ); + setSpacing( 10 ); + +/* + TQLabel *lab = new TQLabel( tr("TROLL PRINT"), this ); + lab->setAlignment( AlignCenter ); +*/ + + TQRadioButton *but; + + TQHButtonGroup *twoSided = new TQHButtonGroup( this ); + twoSided->setTitle( tr("2-sided") ); + but = new TQRadioButton( tr("Enabled"), twoSided ); + but = new TQRadioButton( tr("Disabled"), twoSided ); + but->toggle(); + + TQHButtonGroup *colors = new TQHButtonGroup( this ); + colors->setTitle( tr("Colors") ); + but = new TQRadioButton( tr("Enabled"), colors ); + but = new TQRadioButton( tr("Disabled"), colors ); + but->toggle(); +} diff --git a/tools/linguist/tutorial/tt3/printpanel.h b/tools/linguist/tutorial/tt3/printpanel.h new file mode 100644 index 000000000..8b1f9bc60 --- /dev/null +++ b/tools/linguist/tutorial/tt3/printpanel.h @@ -0,0 +1,19 @@ +/**************************************************************** +** +** Definition of PrintPanel class, translation tutorial 3 +** +****************************************************************/ + +#ifndef PRINTPANEL_H +#define PRINTPANEL_H + +#include + +class PrintPanel : public TQVBox +{ + Q_OBJECT +public: + PrintPanel( TQWidget *parent = 0, const char *name = 0 ); +}; + +#endif diff --git a/tools/linguist/tutorial/tt3/tt3.pro b/tools/linguist/tutorial/tt3/tt3.pro new file mode 100644 index 000000000..c219d1e83 --- /dev/null +++ b/tools/linguist/tutorial/tt3/tt3.pro @@ -0,0 +1,8 @@ +TEMPLATE = app +CONFIG += qt warn_on +HEADERS = mainwindow.h \ + printpanel.h +SOURCES = main.cpp \ + mainwindow.cpp \ + printpanel.cpp +TRANSLATIONS = tt3_pt.ts diff --git a/tools/linguist/tutorial/tt3/tt3_pt.ts b/tools/linguist/tutorial/tt3/tt3_pt.ts new file mode 100644 index 000000000..cf8ff4f63 --- /dev/null +++ b/tools/linguist/tutorial/tt3/tt3_pt.ts @@ -0,0 +1,65 @@ + + + MainWindow + + Troll Print 1.0 + Troll Imprimir 1.0 + + + E&xit + &Sair + + + &About + &Sobre + + + About &Qt + Sobre &Qt + + + &File + &Arquivo + + + &Help + A&juda + + + About Troll Print 1.0 + Sobre Troll Imprimir 1.0 + + + Troll Print 1.0. + +Copyright 1999 Macroshaft, Inc. + Troll Imprimir 1.0 + +Copyright 1999 Macroshaft, Inc. + + + Ctrl+Q + Quit + Ctrl+Q + + + + PrintPanel + + 2-sided + 2-lados + + + Enabled + Ativado + + + Disabled + Desativado + + + Colors + Cores + + + -- cgit v1.2.1