summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authoradjam <adjam@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-05-03 23:51:22 +0000
committeradjam <adjam@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-05-03 23:51:22 +0000
commitc0190e41f7f2e5fe30fa8556fa35f43950afbfdb (patch)
tree086794c886f413b3e4dbcfad9d3697a55f8dd64b
parentInitial rekcommit.. (diff)
downloadrekonq-c0190e41f7f2e5fe30fa8556fa35f43950afbfdb.tar.xz
Importing recode (rekonq code).
I'm sorry I coudn't perform this with gitsvn or tailor.. but I cannot lose all the evening just for this. And I need to sleep now.. git-svn-id: svn+ssh://svn.kde.org/home/kde/trunk/playground/network/rekonq@963146 283d02a7-25f6-0310-bc7c-ecb5cbfe19da
-rw-r--r--AUTHORS4
-rw-r--r--CMakeLists.txt98
-rw-r--r--COPYING674
-rw-r--r--ChangeLog26
-rw-r--r--INSTALL27
-rw-r--r--data/CMakeLists.txt24
-rw-r--r--data/defaultbookmarks.xbel22
-rw-r--r--data/loading.gifbin0 -> 847 bytes
-rw-r--r--data/notfound.html66
-rw-r--r--data/rekonq.desktop12
-rw-r--r--data/slack-desc12
-rw-r--r--data/webkit-icon.pngbin0 -> 25694 bytes
-rw-r--r--doc/CMakeLists.txt4
-rw-r--r--doc/index.docbook327
-rw-r--r--icons/CMakeLists.txt2
-rw-r--r--icons/hi16-app-rekonq.pngbin0 -> 887 bytes
-rw-r--r--icons/hi32-app-rekonq.pngbin0 -> 2269 bytes
-rw-r--r--icons/hi64-app-rekonq.pngbin0 -> 6071 bytes
-rw-r--r--po/CMakeLists.txt34
-rw-r--r--po/rekonq.pot1007
-rw-r--r--po/rekonq_de.po1099
-rw-r--r--po/rekonq_it.po1038
-rw-r--r--po/rekonq_ru.po1134
-rw-r--r--rekonq.SlackBuild79
-rwxr-xr-xscripts/codingstyle.sh48
-rwxr-xr-xscripts/i18n.sh41
-rw-r--r--src/CMakeLists.txt63
-rw-r--r--src/application.cpp206
-rw-r--r--src/application.h115
-rw-r--r--src/autosaver.cpp90
-rw-r--r--src/autosaver.h55
-rw-r--r--src/bookmarks.cpp278
-rw-r--r--src/bookmarks.h238
-rw-r--r--src/cookiejar.cpp841
-rw-r--r--src/cookiejar.h200
-rw-r--r--src/cookies.ui107
-rw-r--r--src/cookiesexceptions.ui179
-rw-r--r--src/download.cpp224
-rw-r--r--src/download.h141
-rw-r--r--src/edittableview.cpp61
-rw-r--r--src/edittableview.h42
-rw-r--r--src/edittreeview.cpp61
-rw-r--r--src/edittreeview.h41
-rw-r--r--src/findbar.cpp137
-rw-r--r--src/findbar.h61
-rw-r--r--src/history.cpp1459
-rw-r--r--src/history.h402
-rw-r--r--src/history.ui101
-rw-r--r--src/lineedit.cpp85
-rw-r--r--src/lineedit.h50
-rw-r--r--src/main.cpp98
-rw-r--r--src/mainview.cpp716
-rw-r--r--src/mainview.h198
-rw-r--r--src/mainwindow.cpp930
-rw-r--r--src/mainwindow.h153
-rw-r--r--src/modelmenu.cpp228
-rw-r--r--src/modelmenu.h92
-rw-r--r--src/networkaccessmanager.cpp165
-rw-r--r--src/networkaccessmanager.h47
-rw-r--r--src/panelhistory.cpp95
-rw-r--r--src/panelhistory.h55
-rw-r--r--src/password.ui69
-rw-r--r--src/proxy.ui62
-rw-r--r--src/rekonq.kcfg119
-rw-r--r--src/rekonq.kcfgc5
-rw-r--r--src/rekonqui.rc104
-rw-r--r--src/searchbar.cpp129
-rw-r--r--src/searchbar.h67
-rw-r--r--src/settings.cpp212
-rw-r--r--src/settings.h55
-rw-r--r--src/settings_fonts.ui97
-rw-r--r--src/settings_general.ui142
-rw-r--r--src/settings_privacy.ui168
-rw-r--r--src/settings_proxy.ui152
-rw-r--r--src/settings_webkit.ui134
-rw-r--r--src/sidepanel.cpp53
-rw-r--r--src/sidepanel.h50
-rw-r--r--src/stackedurlbar.cpp152
-rw-r--r--src/stackedurlbar.h64
-rw-r--r--src/tabbar.cpp145
-rw-r--r--src/tabbar.h78
-rw-r--r--src/urlbar.cpp240
-rw-r--r--src/urlbar.h99
-rw-r--r--src/webview.cpp504
-rw-r--r--src/webview.h155
85 files changed, 16847 insertions, 0 deletions
diff --git a/AUTHORS b/AUTHORS
new file mode 100644
index 00000000..386a41d2
--- /dev/null
+++ b/AUTHORS
@@ -0,0 +1,4 @@
+Andrea Diamantini adjam7_AT_gmail_DOT_com Project Lead, Developer, Italian translation
+Alexander Domrachev alexander.domrachev_AT_gmail_DOT_com Developer, Russian translation
+Pawel Prazak kojots350_AT_gmail_DOT_com Developer
+snagiotis Papadopoulos pano_90@gmx.net German translation
diff --git a/CMakeLists.txt b/CMakeLists.txt
new file mode 100644
index 00000000..4cbc3de2
--- /dev/null
+++ b/CMakeLists.txt
@@ -0,0 +1,98 @@
+# Andrea Diamantini - adjam7 at gmail dot com
+# rekonq project
+
+PROJECT( rekonq )
+
+# ===============================================================================================
+# Informations to update before to release this package.
+
+# rekonq info
+SET(REKONQ_MAJOR_VERSION "0")
+SET(REKONQ_MINOR_VERSION "1")
+SET(REKONQ_PATCH_VERSION "0alpha")
+
+SET(REKONQ_VERSION_STR
+ "${REKONQ_MAJOR_VERSION}.${REKONQ_MINOR_VERSION}.${REKONQ_PATCH_VERSION}"
+ )
+
+SET(REKONQ_SITE "http://rekonq.sourceforge.net")
+
+# =================================================================================================
+# minimum cmake required
+
+CMAKE_MINIMUM_REQUIRED(VERSION 2.6.2)
+
+# =================================================================================================
+
+
+SET(QT_MIN_VERSION 4.5.0)
+FIND_PACKAGE(Qt4 REQUIRED)
+SET(KDE_MIN_VERSION 4.2.0)
+FIND_PACKAGE(KDE4 REQUIRED)
+
+INCLUDE(MacroOptionalFindPackage)
+INCLUDE(FindPackageHandleStandardArgs)
+INCLUDE(KDE4Defaults)
+INCLUDE(MacroLibrary)
+
+# ==================================================================================================
+# Log messages
+
+MESSAGE(STATUS "")
+MESSAGE(STATUS "----------------------------------------------------------------------------------")
+MESSAGE(STATUS " rekonq ${REKONQ_VERSION_STR} dependencies results <${REKONQ_SITE}>")
+
+# Require shared libraries results.
+
+SET(QT_VERS_STR
+ "${QT_VERSION_MAJOR}.${QT_VERSION_MINOR}.${QT_VERSION_PATCH}"
+ )
+
+IF(QT_FOUND)
+ MESSAGE(STATUS " Qt library found............... YES")
+ MESSAGE(STATUS " Qt version ${QT_VERS_STR} found! ")
+ELSE(QT_FOUND)
+ MESSAGE(STATUS " Qt library found............... NO")
+ MESSAGE(STATUS "")
+ MESSAGE(SEND_ERROR " rekonq needs at least Qt ${QT_MIN_VERSION}. Please install it and try compiling again.")
+ MESSAGE(STATUS " Qt website is at http://www.qtsoftware.com")
+ MESSAGE(STATUS "")
+ENDIF(QT_FOUND)
+
+MESSAGE(STATUS "----------------------------------------------------------------------------------")
+MESSAGE(STATUS "")
+
+# Optional plugins results.
+
+IF(QT_FOUND)
+ MESSAGE(STATUS " rekonq will be compiled....... YES")
+ SET(REKONQ_CAN_BE_COMPILED true)
+ELSE(QT_FOUND)
+ MESSAGE(FATAL_ERROR " rekonq will NOT be compiled!")
+ SET(REKONQ_CAN_BE_COMPILED false)
+ENDIF(QT_FOUND)
+
+MESSAGE(STATUS "----------------------------------------------------------------------------------")
+MESSAGE(STATUS "")
+
+# ==================================================================================================
+
+IF(REKONQ_CAN_BE_COMPILED)
+
+ INCLUDE_DIRECTORIES( ${CMAKE_CURRENT_SOURCE_DIR}
+ ${CMAKE_CURRENT_BINARY_DIR}
+ ${KDE4_INCLUDES}
+ ${QT4_INCLUDES}
+ ${QT_QTNETWORK_INCLUDE_DIR}
+ ${QT_QTWEBKIT_INCLUDE_DIR}
+ )
+
+ ADD_SUBDIRECTORY( src )
+ ADD_SUBDIRECTORY( icons )
+ ADD_SUBDIRECTORY( data )
+ ADD_SUBDIRECTORY( po )
+# ADD_SUBDIRECTORY( doc )
+
+ENDIF(REKONQ_CAN_BE_COMPILED)
+
+# =====================================================================================================
diff --git a/COPYING b/COPYING
new file mode 100644
index 00000000..94a9ed02
--- /dev/null
+++ b/COPYING
@@ -0,0 +1,674 @@
+ GNU GENERAL PUBLIC LICENSE
+ Version 3, 29 June 2007
+
+ Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+ Preamble
+
+ The GNU General Public License is a free, copyleft license for
+software and other kinds of works.
+
+ The licenses for most software and other practical works are designed
+to take away your freedom to share and change the works. By contrast,
+the GNU General Public License is intended to guarantee your freedom to
+share and change all versions of a program--to make sure it remains free
+software for all its users. We, the Free Software Foundation, use the
+GNU General Public License for most of our software; it applies also to
+any other work released this way by its authors. You can apply it to
+your programs, too.
+
+ When we speak of free software, we are referring to freedom, not
+price. Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+them if you wish), that you receive source code or can get it if you
+want it, that you can change the software or use pieces of it in new
+free programs, and that you know you can do these things.
+
+ To protect your rights, we need to prevent others from denying you
+these rights or asking you to surrender the rights. Therefore, you have
+certain responsibilities if you distribute copies of the software, or if
+you modify it: responsibilities to respect the freedom of others.
+
+ For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must pass on to the recipients the same
+freedoms that you received. You must make sure that they, too, receive
+or can get the source code. And you must show them these terms so they
+know their rights.
+
+ Developers that use the GNU GPL protect your rights with two steps:
+(1) assert copyright on the software, and (2) offer you this License
+giving you legal permission to copy, distribute and/or modify it.
+
+ For the developers' and authors' protection, the GPL clearly explains
+that there is no warranty for this free software. For both users' and
+authors' sake, the GPL requires that modified versions be marked as
+changed, so that their problems will not be attributed erroneously to
+authors of previous versions.
+
+ Some devices are designed to deny users access to install or run
+modified versions of the software inside them, although the manufacturer
+can do so. This is fundamentally incompatible with the aim of
+protecting users' freedom to change the software. The systematic
+pattern of such abuse occurs in the area of products for individuals to
+use, which is precisely where it is most unacceptable. Therefore, we
+have designed this version of the GPL to prohibit the practice for those
+products. If such problems arise substantially in other domains, we
+stand ready to extend this provision to those domains in future versions
+of the GPL, as needed to protect the freedom of users.
+
+ Finally, every program is threatened constantly by software patents.
+States should not allow patents to restrict development and use of
+software on general-purpose computers, but in those that do, we wish to
+avoid the special danger that patents applied to a free program could
+make it effectively proprietary. To prevent this, the GPL assures that
+patents cannot be used to render the program non-free.
+
+ The precise terms and conditions for copying, distribution and
+modification follow.
+
+ TERMS AND CONDITIONS
+
+ 0. Definitions.
+
+ "This License" refers to version 3 of the GNU General Public License.
+
+ "Copyright" also means copyright-like laws that apply to other kinds of
+works, such as semiconductor masks.
+
+ "The Program" refers to any copyrightable work licensed under this
+License. Each licensee is addressed as "you". "Licensees" and
+"recipients" may be individuals or organizations.
+
+ To "modify" a work means to copy from or adapt all or part of the work
+in a fashion requiring copyright permission, other than the making of an
+exact copy. The resulting work is called a "modified version" of the
+earlier work or a work "based on" the earlier work.
+
+ A "covered work" means either the unmodified Program or a work based
+on the Program.
+
+ To "propagate" a work means to do anything with it that, without
+permission, would make you directly or secondarily liable for
+infringement under applicable copyright law, except executing it on a
+computer or modifying a private copy. Propagation includes copying,
+distribution (with or without modification), making available to the
+public, and in some countries other activities as well.
+
+ To "convey" a work means any kind of propagation that enables other
+parties to make or receive copies. Mere interaction with a user through
+a computer network, with no transfer of a copy, is not conveying.
+
+ An interactive user interface displays "Appropriate Legal Notices"
+to the extent that it includes a convenient and prominently visible
+feature that (1) displays an appropriate copyright notice, and (2)
+tells the user that there is no warranty for the work (except to the
+extent that warranties are provided), that licensees may convey the
+work under this License, and how to view a copy of this License. If
+the interface presents a list of user commands or options, such as a
+menu, a prominent item in the list meets this criterion.
+
+ 1. Source Code.
+
+ The "source code" for a work means the preferred form of the work
+for making modifications to it. "Object code" means any non-source
+form of a work.
+
+ A "Standard Interface" means an interface that either is an official
+standard defined by a recognized standards body, or, in the case of
+interfaces specified for a particular programming language, one that
+is widely used among developers working in that language.
+
+ The "System Libraries" of an executable work include anything, other
+than the work as a whole, that (a) is included in the normal form of
+packaging a Major Component, but which is not part of that Major
+Component, and (b) serves only to enable use of the work with that
+Major Component, or to implement a Standard Interface for which an
+implementation is available to the public in source code form. A
+"Major Component", in this context, means a major essential component
+(kernel, window system, and so on) of the specific operating system
+(if any) on which the executable work runs, or a compiler used to
+produce the work, or an object code interpreter used to run it.
+
+ The "Corresponding Source" for a work in object code form means all
+the source code needed to generate, install, and (for an executable
+work) run the object code and to modify the work, including scripts to
+control those activities. However, it does not include the work's
+System Libraries, or general-purpose tools or generally available free
+programs which are used unmodified in performing those activities but
+which are not part of the work. For example, Corresponding Source
+includes interface definition files associated with source files for
+the work, and the source code for shared libraries and dynamically
+linked subprograms that the work is specifically designed to require,
+such as by intimate data communication or control flow between those
+subprograms and other parts of the work.
+
+ The Corresponding Source need not include anything that users
+can regenerate automatically from other parts of the Corresponding
+Source.
+
+ The Corresponding Source for a work in source code form is that
+same work.
+
+ 2. Basic Permissions.
+
+ All rights granted under this License are granted for the term of
+copyright on the Program, and are irrevocable provided the stated
+conditions are met. This License explicitly affirms your unlimited
+permission to run the unmodified Program. The output from running a
+covered work is covered by this License only if the output, given its
+content, constitutes a covered work. This License acknowledges your
+rights of fair use or other equivalent, as provided by copyright law.
+
+ You may make, run and propagate covered works that you do not
+convey, without conditions so long as your license otherwise remains
+in force. You may convey covered works to others for the sole purpose
+of having them make modifications exclusively for you, or provide you
+with facilities for running those works, provided that you comply with
+the terms of this License in conveying all material for which you do
+not control copyright. Those thus making or running the covered works
+for you must do so exclusively on your behalf, under your direction
+and control, on terms that prohibit them from making any copies of
+your copyrighted material outside their relationship with you.
+
+ Conveying under any other circumstances is permitted solely under
+the conditions stated below. Sublicensing is not allowed; section 10
+makes it unnecessary.
+
+ 3. Protecting Users' Legal Rights From Anti-Circumvention Law.
+
+ No covered work shall be deemed part of an effective technological
+measure under any applicable law fulfilling obligations under article
+11 of the WIPO copyright treaty adopted on 20 December 1996, or
+similar laws prohibiting or restricting circumvention of such
+measures.
+
+ When you convey a covered work, you waive any legal power to forbid
+circumvention of technological measures to the extent such circumvention
+is effected by exercising rights under this License with respect to
+the covered work, and you disclaim any intention to limit operation or
+modification of the work as a means of enforcing, against the work's
+users, your or third parties' legal rights to forbid circumvention of
+technological measures.
+
+ 4. Conveying Verbatim Copies.
+
+ You may convey verbatim copies of the Program's source code as you
+receive it, in any medium, provided that you conspicuously and
+appropriately publish on each copy an appropriate copyright notice;
+keep intact all notices stating that this License and any
+non-permissive terms added in accord with section 7 apply to the code;
+keep intact all notices of the absence of any warranty; and give all
+recipients a copy of this License along with the Program.
+
+ You may charge any price or no price for each copy that you convey,
+and you may offer support or warranty protection for a fee.
+
+ 5. Conveying Modified Source Versions.
+
+ You may convey a work based on the Program, or the modifications to
+produce it from the Program, in the form of source code under the
+terms of section 4, provided that you also meet all of these conditions:
+
+ a) The work must carry prominent notices stating that you modified
+ it, and giving a relevant date.
+
+ b) The work must carry prominent notices stating that it is
+ released under this License and any conditions added under section
+ 7. This requirement modifies the requirement in section 4 to
+ "keep intact all notices".
+
+ c) You must license the entire work, as a whole, under this
+ License to anyone who comes into possession of a copy. This
+ License will therefore apply, along with any applicable section 7
+ additional terms, to the whole of the work, and all its parts,
+ regardless of how they are packaged. This License gives no
+ permission to license the work in any other way, but it does not
+ invalidate such permission if you have separately received it.
+
+ d) If the work has interactive user interfaces, each must display
+ Appropriate Legal Notices; however, if the Program has interactive
+ interfaces that do not display Appropriate Legal Notices, your
+ work need not make them do so.
+
+ A compilation of a covered work with other separate and independent
+works, which are not by their nature extensions of the covered work,
+and which are not combined with it such as to form a larger program,
+in or on a volume of a storage or distribution medium, is called an
+"aggregate" if the compilation and its resulting copyright are not
+used to limit the access or legal rights of the compilation's users
+beyond what the individual works permit. Inclusion of a covered work
+in an aggregate does not cause this License to apply to the other
+parts of the aggregate.
+
+ 6. Conveying Non-Source Forms.
+
+ You may convey a covered work in object code form under the terms
+of sections 4 and 5, provided that you also convey the
+machine-readable Corresponding Source under the terms of this License,
+in one of these ways:
+
+ a) Convey the object code in, or embodied in, a physical product
+ (including a physical distribution medium), accompanied by the
+ Corresponding Source fixed on a durable physical medium
+ customarily used for software interchange.
+
+ b) Convey the object code in, or embodied in, a physical product
+ (including a physical distribution medium), accompanied by a
+ written offer, valid for at least three years and valid for as
+ long as you offer spare parts or customer support for that product
+ model, to give anyone who possesses the object code either (1) a
+ copy of the Corresponding Source for all the software in the
+ product that is covered by this License, on a durable physical
+ medium customarily used for software interchange, for a price no
+ more than your reasonable cost of physically performing this
+ conveying of source, or (2) access to copy the
+ Corresponding Source from a network server at no charge.
+
+ c) Convey individual copies of the object code with a copy of the
+ written offer to provide the Corresponding Source. This
+ alternative is allowed only occasionally and noncommercially, and
+ only if you received the object code with such an offer, in accord
+ with subsection 6b.
+
+ d) Convey the object code by offering access from a designated
+ place (gratis or for a charge), and offer equivalent access to the
+ Corresponding Source in the same way through the same place at no
+ further charge. You need not require recipients to copy the
+ Corresponding Source along with the object code. If the place to
+ copy the object code is a network server, the Corresponding Source
+ may be on a different server (operated by you or a third party)
+ that supports equivalent copying facilities, provided you maintain
+ clear directions next to the object code saying where to find the
+ Corresponding Source. Regardless of what server hosts the
+ Corresponding Source, you remain obligated to ensure that it is
+ available for as long as needed to satisfy these requirements.
+
+ e) Convey the object code using peer-to-peer transmission, provided
+ you inform other peers where the object code and Corresponding
+ Source of the work are being offered to the general public at no
+ charge under subsection 6d.
+
+ A separable portion of the object code, whose source code is excluded
+from the Corresponding Source as a System Library, need not be
+included in conveying the object code work.
+
+ A "User Product" is either (1) a "consumer product", which means any
+tangible personal property which is normally used for personal, family,
+or household purposes, or (2) anything designed or sold for incorporation
+into a dwelling. In determining whether a product is a consumer product,
+doubtful cases shall be resolved in favor of coverage. For a particular
+product received by a particular user, "normally used" refers to a
+typical or common use of that class of product, regardless of the status
+of the particular user or of the way in which the particular user
+actually uses, or expects or is expected to use, the product. A product
+is a consumer product regardless of whether the product has substantial
+commercial, industrial or non-consumer uses, unless such uses represent
+the only significant mode of use of the product.
+
+ "Installation Information" for a User Product means any methods,
+procedures, authorization keys, or other information required to install
+and execute modified versions of a covered work in that User Product from
+a modified version of its Corresponding Source. The information must
+suffice to ensure that the continued functioning of the modified object
+code is in no case prevented or interfered with solely because
+modification has been made.
+
+ If you convey an object code work under this section in, or with, or
+specifically for use in, a User Product, and the conveying occurs as
+part of a transaction in which the right of possession and use of the
+User Product is transferred to the recipient in perpetuity or for a
+fixed term (regardless of how the transaction is characterized), the
+Corresponding Source conveyed under this section must be accompanied
+by the Installation Information. But this requirement does not apply
+if neither you nor any third party retains the ability to install
+modified object code on the User Product (for example, the work has
+been installed in ROM).
+
+ The requirement to provide Installation Information does not include a
+requirement to continue to provide support service, warranty, or updates
+for a work that has been modified or installed by the recipient, or for
+the User Product in which it has been modified or installed. Access to a
+network may be denied when the modification itself materially and
+adversely affects the operation of the network or violates the rules and
+protocols for communication across the network.
+
+ Corresponding Source conveyed, and Installation Information provided,
+in accord with this section must be in a format that is publicly
+documented (and with an implementation available to the public in
+source code form), and must require no special password or key for
+unpacking, reading or copying.
+
+ 7. Additional Terms.
+
+ "Additional permissions" are terms that supplement the terms of this
+License by making exceptions from one or more of its conditions.
+Additional permissions that are applicable to the entire Program shall
+be treated as though they were included in this License, to the extent
+that they are valid under applicable law. If additional permissions
+apply only to part of the Program, that part may be used separately
+under those permissions, but the entire Program remains governed by
+this License without regard to the additional permissions.
+
+ When you convey a copy of a covered work, you may at your option
+remove any additional permissions from that copy, or from any part of
+it. (Additional permissions may be written to require their own
+removal in certain cases when you modify the work.) You may place
+additional permissions on material, added by you to a covered work,
+for which you have or can give appropriate copyright permission.
+
+ Notwithstanding any other provision of this License, for material you
+add to a covered work, you may (if authorized by the copyright holders of
+that material) supplement the terms of this License with terms:
+
+ a) Disclaiming warranty or limiting liability differently from the
+ terms of sections 15 and 16 of this License; or
+
+ b) Requiring preservation of specified reasonable legal notices or
+ author attributions in that material or in the Appropriate Legal
+ Notices displayed by works containing it; or
+
+ c) Prohibiting misrepresentation of the origin of that material, or
+ requiring that modified versions of such material be marked in
+ reasonable ways as different from the original version; or
+
+ d) Limiting the use for publicity purposes of names of licensors or
+ authors of the material; or
+
+ e) Declining to grant rights under trademark law for use of some
+ trade names, trademarks, or service marks; or
+
+ f) Requiring indemnification of licensors and authors of that
+ material by anyone who conveys the material (or modified versions of
+ it) with contractual assumptions of liability to the recipient, for
+ any liability that these contractual assumptions directly impose on
+ those licensors and authors.
+
+ All other non-permissive additional terms are considered "further
+restrictions" within the meaning of section 10. If the Program as you
+received it, or any part of it, contains a notice stating that it is
+governed by this License along with a term that is a further
+restriction, you may remove that term. If a license document contains
+a further restriction but permits relicensing or conveying under this
+License, you may add to a covered work material governed by the terms
+of that license document, provided that the further restriction does
+not survive such relicensing or conveying.
+
+ If you add terms to a covered work in accord with this section, you
+must place, in the relevant source files, a statement of the
+additional terms that apply to those files, or a notice indicating
+where to find the applicable terms.
+
+ Additional terms, permissive or non-permissive, may be stated in the
+form of a separately written license, or stated as exceptions;
+the above requirements apply either way.
+
+ 8. Termination.
+
+ You may not propagate or modify a covered work except as expressly
+provided under this License. Any attempt otherwise to propagate or
+modify it is void, and will automatically terminate your rights under
+this License (including any patent licenses granted under the third
+paragraph of section 11).
+
+ However, if you cease all violation of this License, then your
+license from a particular copyright holder is reinstated (a)
+provisionally, unless and until the copyright holder explicitly and
+finally terminates your license, and (b) permanently, if the copyright
+holder fails to notify you of the violation by some reasonable means
+prior to 60 days after the cessation.
+
+ Moreover, your license from a particular copyright holder is
+reinstated permanently if the copyright holder notifies you of the
+violation by some reasonable means, this is the first time you have
+received notice of violation of this License (for any work) from that
+copyright holder, and you cure the violation prior to 30 days after
+your receipt of the notice.
+
+ Termination of your rights under this section does not terminate the
+licenses of parties who have received copies or rights from you under
+this License. If your rights have been terminated and not permanently
+reinstated, you do not qualify to receive new licenses for the same
+material under section 10.
+
+ 9. Acceptance Not Required for Having Copies.
+
+ You are not required to accept this License in order to receive or
+run a copy of the Program. Ancillary propagation of a covered work
+occurring solely as a consequence of using peer-to-peer transmission
+to receive a copy likewise does not require acceptance. However,
+nothing other than this License grants you permission to propagate or
+modify any covered work. These actions infringe copyright if you do
+not accept this License. Therefore, by modifying or propagating a
+covered work, you indicate your acceptance of this License to do so.
+
+ 10. Automatic Licensing of Downstream Recipients.
+
+ Each time you convey a covered work, the recipient automatically
+receives a license from the original licensors, to run, modify and
+propagate that work, subject to this License. You are not responsible
+for enforcing compliance by third parties with this License.
+
+ An "entity transaction" is a transaction transferring control of an
+organization, or substantially all assets of one, or subdividing an
+organization, or merging organizations. If propagation of a covered
+work results from an entity transaction, each party to that
+transaction who receives a copy of the work also receives whatever
+licenses to the work the party's predecessor in interest had or could
+give under the previous paragraph, plus a right to possession of the
+Corresponding Source of the work from the predecessor in interest, if
+the predecessor has it or can get it with reasonable efforts.
+
+ You may not impose any further restrictions on the exercise of the
+rights granted or affirmed under this License. For example, you may
+not impose a license fee, royalty, or other charge for exercise of
+rights granted under this License, and you may not initiate litigation
+(including a cross-claim or counterclaim in a lawsuit) alleging that
+any patent claim is infringed by making, using, selling, offering for
+sale, or importing the Program or any portion of it.
+
+ 11. Patents.
+
+ A "contributor" is a copyright holder who authorizes use under this
+License of the Program or a work on which the Program is based. The
+work thus licensed is called the contributor's "contributor version".
+
+ A contributor's "essential patent claims" are all patent claims
+owned or controlled by the contributor, whether already acquired or
+hereafter acquired, that would be infringed by some manner, permitted
+by this License, of making, using, or selling its contributor version,
+but do not include claims that would be infringed only as a
+consequence of further modification of the contributor version. For
+purposes of this definition, "control" includes the right to grant
+patent sublicenses in a manner consistent with the requirements of
+this License.
+
+ Each contributor grants you a non-exclusive, worldwide, royalty-free
+patent license under the contributor's essential patent claims, to
+make, use, sell, offer for sale, import and otherwise run, modify and
+propagate the contents of its contributor version.
+
+ In the following three paragraphs, a "patent license" is any express
+agreement or commitment, however denominated, not to enforce a patent
+(such as an express permission to practice a patent or covenant not to
+sue for patent infringement). To "grant" such a patent license to a
+party means to make such an agreement or commitment not to enforce a
+patent against the party.
+
+ If you convey a covered work, knowingly relying on a patent license,
+and the Corresponding Source of the work is not available for anyone
+to copy, free of charge and under the terms of this License, through a
+publicly available network server or other readily accessible means,
+then you must either (1) cause the Corresponding Source to be so
+available, or (2) arrange to deprive yourself of the benefit of the
+patent license for this particular work, or (3) arrange, in a manner
+consistent with the requirements of this License, to extend the patent
+license to downstream recipients. "Knowingly relying" means you have
+actual knowledge that, but for the patent license, your conveying the
+covered work in a country, or your recipient's use of the covered work
+in a country, would infringe one or more identifiable patents in that
+country that you have reason to believe are valid.
+
+ If, pursuant to or in connection with a single transaction or
+arrangement, you convey, or propagate by procuring conveyance of, a
+covered work, and grant a patent license to some of the parties
+receiving the covered work authorizing them to use, propagate, modify
+or convey a specific copy of the covered work, then the patent license
+you grant is automatically extended to all recipients of the covered
+work and works based on it.
+
+ A patent license is "discriminatory" if it does not include within
+the scope of its coverage, prohibits the exercise of, or is
+conditioned on the non-exercise of one or more of the rights that are
+specifically granted under this License. You may not convey a covered
+work if you are a party to an arrangement with a third party that is
+in the business of distributing software, under which you make payment
+to the third party based on the extent of your activity of conveying
+the work, and under which the third party grants, to any of the
+parties who would receive the covered work from you, a discriminatory
+patent license (a) in connection with copies of the covered work
+conveyed by you (or copies made from those copies), or (b) primarily
+for and in connection with specific products or compilations that
+contain the covered work, unless you entered into that arrangement,
+or that patent license was granted, prior to 28 March 2007.
+
+ Nothing in this License shall be construed as excluding or limiting
+any implied license or other defenses to infringement that may
+otherwise be available to you under applicable patent law.
+
+ 12. No Surrender of Others' Freedom.
+
+ If conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License. If you cannot convey a
+covered work so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you may
+not convey it at all. For example, if you agree to terms that obligate you
+to collect a royalty for further conveying from those to whom you convey
+the Program, the only way you could satisfy both those terms and this
+License would be to refrain entirely from conveying the Program.
+
+ 13. Use with the GNU Affero General Public License.
+
+ Notwithstanding any other provision of this License, you have
+permission to link or combine any covered work with a work licensed
+under version 3 of the GNU Affero General Public License into a single
+combined work, and to convey the resulting work. The terms of this
+License will continue to apply to the part which is the covered work,
+but the special requirements of the GNU Affero General Public License,
+section 13, concerning interaction through a network will apply to the
+combination as such.
+
+ 14. Revised Versions of this License.
+
+ The Free Software Foundation may publish revised and/or new versions of
+the GNU General Public License from time to time. Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+ Each version is given a distinguishing version number. If the
+Program specifies that a certain numbered version of the GNU General
+Public License "or any later version" applies to it, you have the
+option of following the terms and conditions either of that numbered
+version or of any later version published by the Free Software
+Foundation. If the Program does not specify a version number of the
+GNU General Public License, you may choose any version ever published
+by the Free Software Foundation.
+
+ If the Program specifies that a proxy can decide which future
+versions of the GNU General Public License can be used, that proxy's
+public statement of acceptance of a version permanently authorizes you
+to choose that version for the Program.
+
+ Later license versions may give you additional or different
+permissions. However, no additional obligations are imposed on any
+author or copyright holder as a result of your choosing to follow a
+later version.
+
+ 15. Disclaimer of Warranty.
+
+ THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY
+APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT
+HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY
+OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO,
+THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM
+IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF
+ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
+
+ 16. Limitation of Liability.
+
+ IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
+THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY
+GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
+USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF
+DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD
+PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS),
+EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
+SUCH DAMAGES.
+
+ 17. Interpretation of Sections 15 and 16.
+
+ If the disclaimer of warranty and limitation of liability provided
+above cannot be given local legal effect according to their terms,
+reviewing courts shall apply local law that most closely approximates
+an absolute waiver of all civil liability in connection with the
+Program, unless a warranty or assumption of liability accompanies a
+copy of the Program in return for a fee.
+
+ END OF TERMS AND CONDITIONS
+
+ How to Apply These Terms to Your New Programs
+
+ If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+ To do so, attach the following notices to the program. It is safest
+to attach them to the start of each source file to most effectively
+state the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+ <one line to give the program's name and a brief idea of what it does.>
+ Copyright (C) <year> <name of author>
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+Also add information on how to contact you by electronic and paper mail.
+
+ If the program does terminal interaction, make it output a short
+notice like this when it starts in an interactive mode:
+
+ <program> Copyright (C) <year> <name of author>
+ This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+ This is free software, and you are welcome to redistribute it
+ under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License. Of course, your program's commands
+might be different; for a GUI interface, you would use an "about box".
+
+ You should also get your employer (if you work as a programmer) or school,
+if any, to sign a "copyright disclaimer" for the program, if necessary.
+For more information on this, and how to apply and follow the GNU GPL, see
+<http://www.gnu.org/licenses/>.
+
+ The GNU General Public License does not permit incorporating your program
+into proprietary programs. If your program is a subroutine library, you
+may consider it more useful to permit linking proprietary applications with
+the library. If this is what you want to do, use the GNU Lesser General
+Public License instead of this License. But first, please read
+<http://www.gnu.org/philosophy/why-not-lgpl.html>.
diff --git a/ChangeLog b/ChangeLog
new file mode 100644
index 00000000..1c830037
--- /dev/null
+++ b/ChangeLog
@@ -0,0 +1,26 @@
+0.0.4
+- Rekonq Singleton app
+- With Qt 4.5, preliminary flash support
+- Fixed tabbar actions
+- Fixed System Font Loading
+- improved bookmarks system
+
+0.0.3
+- ~80% ported to KDE4
+- use KConfigXT
+- improved text search bar
+- fixed all "web actions"
+- KDE download system
+- new bookmark toolbar (1st implementation)
+
+0.0.2
+- 70% ported to KDE4
+- new urlbar
+- new searchbar (just Google, for now)
+- new findbar (A-LA kate)
+- Slackware Slackbuild available
+
+
+0.0.1
+- initial porting to KDE4
+- share konqueror bookmarks
diff --git a/INSTALL b/INSTALL
new file mode 100644
index 00000000..3d8888a0
--- /dev/null
+++ b/INSTALL
@@ -0,0 +1,27 @@
+===== Building rekonq from sources =====
+
+=== Prerequisites ===
+
+Qt4.4.x:
+
+ Qt should be prepackaged for all mayor linux distributions. Please see
+ http://www.trolltech.com/products/qt for more information and installation
+ instructions.
+
+KDE 4
+
+ KDE 4.1 (or better) should be prepackaged for all mayor linux distributions. Please see
+ http://techbase.kde.org/Getting_Started/Build/stable_Version
+ for instructions on how to build and setup a KDE4 environment to work in.
+
+
+=== Building rekonq ===
+
+ To build it do the following after switching into the source directory:
+
+ mkdir build && cd build
+ cmake ..
+ make && make install
+
+Enjoy.
+adjam
diff --git a/data/CMakeLists.txt b/data/CMakeLists.txt
new file mode 100644
index 00000000..e4535e07
--- /dev/null
+++ b/data/CMakeLists.txt
@@ -0,0 +1,24 @@
+INSTALL(
+ FILES loading.gif
+ DESTINATION ${DATA_INSTALL_DIR}/rekonq/pics
+)
+
+INSTALL(
+ FILES defaultbookmarks.xbel
+ DESTINATION ${DATA_INSTALL_DIR}/rekonq
+)
+
+INSTALL(
+ FILES rekonq.desktop
+ DESTINATION ${XDG_APPS_INSTALL_DIR}
+)
+
+INSTALL(
+ FILES notfound.html
+ DESTINATION ${DATA_INSTALL_DIR}/rekonq/htmls
+)
+
+INSTALL(
+ FILES webkit-icon.png
+ DESTINATION ${DATA_INSTALL_DIR}/rekonq/pics
+) \ No newline at end of file
diff --git a/data/defaultbookmarks.xbel b/data/defaultbookmarks.xbel
new file mode 100644
index 00000000..b4919c5c
--- /dev/null
+++ b/data/defaultbookmarks.xbel
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE xbel>
+<xbel version="1.0">
+ <bookmark href="http://qtsoftware.com/">
+ <title>QtSoftware</title>
+ </bookmark>
+ <bookmark href="http://webkit.org/">
+ <title>WebKit.org</title>
+ </bookmark>
+ <bookmark href="http://rekonq.sourceforge.net/">
+ <title>rekonq site</title>
+ </bookmark>
+ <bookmark href="http://labs.trolltech.com/">
+ <title>Trolltech Labs</title>
+ </bookmark>
+ <bookmark href="http://kde-apps.org/">
+ <title>KDE-Apps.org</title>
+ </bookmark>
+ <bookmark href="http://www.kde.org/">
+ <title>KDE site</title>
+ </bookmark>
+</xbel>
diff --git a/data/loading.gif b/data/loading.gif
new file mode 100644
index 00000000..c1545eb0
--- /dev/null
+++ b/data/loading.gif
Binary files differ
diff --git a/data/notfound.html b/data/notfound.html
new file mode 100644
index 00000000..09039eb1
--- /dev/null
+++ b/data/notfound.html
@@ -0,0 +1,66 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
+<head>
+<title>%1</title>
+<style type="text/css">
+body {
+ padding: 3em 0em;
+ background: #eeeeee;
+}
+hr {
+ color: lightgray;
+ width: 100%;
+}
+img {
+ float: left;
+ opacity: .8;
+}
+#box {
+ background: white;
+ border: 1px solid lightgray;
+ width: 600px;
+ padding: 60px;
+ margin: auto;
+}
+h1 {
+ font-size: 130%;
+ font-weight: bold;
+ border-bottom: 1px solid lightgray;
+ margin-left: 48px;
+}
+h2 {
+ font-size: 100%;
+ font-weight: normal;
+ border-bottom: 1px solid lightgray;
+ margin-left: 48px;
+}
+ul {
+ font-size: 80%;
+ padding-left: 48px;
+ margin: 0;
+}
+#reloadButton {
+ padding-left: 48px;
+}
+</style>
+</head>
+<body>
+ <div id="box">
+ <img src="%2" width="16" height="16" alt="Not found" />
+ <h1>%3</h1>
+ <h2>When connecting to: %4.</h2>
+ <ul>
+ <li>Check the address for errors such as <b>ww</b>.kde.org
+ instead of <b>www</b>.kde.org</li>
+ <li>If the address is correct, try to check the network
+ connection.</li>
+ <li>If your computer or network is protected by a firewall or
+ proxy, make sure that rekonq is permitted to access
+ the network.</li>
+ <li>Of course, if rekonq doesn't work properly, you can always
+ say it's a programmer error ;)</li>
+ </ul>
+ <br/><br/>
+ </div>
+</body>
+</html>
diff --git a/data/rekonq.desktop b/data/rekonq.desktop
new file mode 100644
index 00000000..599e81ee
--- /dev/null
+++ b/data/rekonq.desktop
@@ -0,0 +1,12 @@
+[Desktop Entry]
+Name=rekonq
+GenericName=Webkit KDE Browser
+Icon=rekonq
+Type=Application
+Exec=rekonq %u
+X-DocPath=rekonq/index.html
+Categories=Qt;KDE;Network;
+Terminal=0
+MimeType=text/html;application/xhtml+xml;application/xml;
+X-DBUS-StartupType=Unique
+X-DBUS-ServiceName=net.sourceforge.rekonq
diff --git a/data/slack-desc b/data/slack-desc
new file mode 100644
index 00000000..3136b228
--- /dev/null
+++ b/data/slack-desc
@@ -0,0 +1,12 @@
+ |-------------------------------------------------------------------|
+rekonq: rekonq (Webkit KDE Browser)
+rekonq:
+rekonq: rekonq is a lightweight KDE browser based on webkit
+rekonq:
+rekonq:
+rekonq:
+rekonq:
+rekonq:
+rekonq:
+rekonq:
+rekonq:
diff --git a/data/webkit-icon.png b/data/webkit-icon.png
new file mode 100644
index 00000000..b3ec677a
--- /dev/null
+++ b/data/webkit-icon.png
Binary files differ
diff --git a/doc/CMakeLists.txt b/doc/CMakeLists.txt
new file mode 100644
index 00000000..3a54287f
--- /dev/null
+++ b/doc/CMakeLists.txt
@@ -0,0 +1,4 @@
+########### install files ###############
+#
+
+kde4_create_handbook(index.docbook INSTALL_DESTINATION ${HTML_INSTALL_DIR}/en SUBDIR rekonq)
diff --git a/doc/index.docbook b/doc/index.docbook
new file mode 100644
index 00000000..32fcb41e
--- /dev/null
+++ b/doc/index.docbook
@@ -0,0 +1,327 @@
+<?xml version="1.0" ?>
+<!DOCTYPE book PUBLIC "-//KDE//DTD DocBook XML V4.2-Based Variant V1.1//EN"
+"dtd/kdex.dtd" [
+ <!ENTITY rekonq "Rekonq">
+ <!ENTITY Andrea.Diamantini "<personname>
+ <firstname>Andrea</firstname>
+ <surname>Diamantini</surname>
+ </personname>
+ ">
+ <!ENTITY Andrea.Diamantini.mail "<email>adjam7@gmail.com</email>">
+ <!ENTITY % addindex "IGNORE">
+ <!ENTITY % English "INCLUDE">
+]>
+
+<book lang="&language;">
+
+<bookinfo>
+<title>The &rekonq; Handbook</title>
+
+<authorgroup>
+<author>&Andrea.Diamantini; &Andrea.Diamantini.mail;</author>
+</authorgroup>
+
+<copyright>
+<year>2008</year>
+<year>2009</year>
+<holder>&Andrea.Diamantini;</holder>
+</copyright>
+
+<legalnotice>&FDLNotice;</legalnotice>
+
+<date>2008-11-16</date>
+<releaseinfo>0.0.4</releaseinfo>
+
+<abstract>
+<para>
+&rekonq; is a lightweight KDE browser based on WebKit.
+</para>
+</abstract>
+
+<keywordset>
+<keyword>KDE</keyword>
+<keyword>browser</keyword>
+<keyword>rekonq</keyword>
+<keyword>webkit</keyword>
+</keywordset>
+
+</bookinfo>
+
+<!-- ================== CHAPTER ================== -->
+
+<chapter id="introduction">
+
+<title>Introduction</title>
+
+<para>
+&rekonq; is a lightweight KDE browser based on WebKit.
+</para>
+
+<sect1 id="starting">
+
+<title>Launching &rekonq;</title>
+
+<para>
+The Find Files tool is a useful method of searching for specific files on your
+computer, or for searching for files that match a pattern. An example of
+this could include searching for files of a particular type or with certain
+letters in the filename.
+
+You can load this utility by clicking on <guimenuitem>Find Files</guimenuitem>. This will
+launch &rekonq;.
+</para>
+
+</sect1>
+
+</chapter>
+
+<!-- ================== CHAPTER ================== -->
+
+<chapter id="kfind">
+<title>Finding Files</title>
+
+<sect1 id="name-tab">
+<title>The Name/Location Tab</title>
+
+<para>
+When starting &rekonq;, you will see a quite simple window. Type in the
+name of the file you are searching in the text box labeled
+<guilabel>Named:</guilabel>. Choose a folder where you want to search
+by typing it in the field <guilabel>Look in:</guilabel>
+or by clicking <guibutton>Browse...</guibutton> and press
+<keycap>Enter</keycap> or click <guibutton>Find</guibutton>. If
+<guilabel>Include subfolders</guilabel> is checked all
+subfolders starting from your chosen folder will be searched
+too. The results will be displayed in the box below.
+</para>
+
+<para>
+You can use the following wildcards:
+</para>
+
+<variablelist>
+<varlistentry>
+<term>The Asterisk <quote><keycap>*</keycap></quote></term>
+<listitem>
+<para>
+The asterisk stands for any number of missing characters (even zero),
+that means &eg; searching for <userinput>marc*</userinput> may find the
+files <filename>marc</filename>, <filename>marc.png</filename> and
+<filename> marc_must_not_read_this.kwd</filename>.
+<userinput>mar*.kwd</userinput> may find
+<filename>marketplace.kwd</filename> and
+<filename>marc_must_not_read_this.kwd</filename>.
+</para>
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term>The Question Mark <quote><keycap>?</keycap></quote></term>
+<listitem>
+<para>
+In contrast to the asterisk, the question mark stands for exactly one
+character, so <userinput>mar?</userinput> will find
+<filename>marc</filename>, but <userinput>marc?</userinput> will not find
+anything, as our files are called <filename>marc</filename> and
+<filename>marc.png</filename>. You can put as many question marks in the
+term as you want, it will find exactly that number of characters.
+</para>
+</listitem>
+</varlistentry>
+
+</variablelist>
+
+<para>
+Of course you can combine those two wildcard symbols in a search term.
+</para>
+
+</sect1>
+
+<sect1 id="kfind-date-range">
+<title>The Contents Tab</title>
+
+<variablelist>
+<varlistentry>
+<term><guilabel>File type</guilabel></term>
+<listitem>
+<para>
+Here you can specify the type of file you are searching for.
+</para>
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term><guilabel>Containing text</guilabel></term>
+<listitem>
+<para>
+Type in the word or phrase the files you are searching for must
+contain. Note: If you do this in a large folder or checked
+<guilabel>Include subfolders</guilabel> in the
+<guilabel>Name/Location</guilabel> tab, this may take a long time.
+</para>
+
+<note>
+<para>This option will <emphasis>not</emphasis> work for all files listed
+under <guilabel>File type</guilabel>. Only the following file types
+are supported:
+
+<itemizedlist>
+<listitem><para>Text files, &eg; source code and <filename>README</filename> files</para></listitem>
+<listitem><para>&kword; &gt;= 1.2</para></listitem>
+<listitem><para>&kpresenter; &gt;= 1.2</para></listitem>
+<listitem><para>&kspread; &gt;= 1.2</para></listitem>
+<listitem><para>OpenOffice.org Writer</para></listitem>
+<listitem><para>OpenOffice.org Impress</para></listitem>
+<listitem><para>OpenOffice.org Calc</para></listitem>
+</itemizedlist>
+
+</para>
+</note>
+
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term><guilabel>Case sensitive</guilabel></term>
+<listitem>
+<para>
+If you enable this option, &rekonq; will
+only find files with the exact case matching, &eg;
+<userinput>MARC</userinput> will only match
+<quote>MARC</quote>, not <quote>Marc</quote>.
+</para>
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term><guilabel>Regular expression</guilabel></term>
+<listitem><para>If you have installed the &kregexpeditor; tool from
+the kdeutils package, you will have this additional option. Enabling
+it will allow you to search for a <firstterm>regexp</firstterm> or
+regular expression. A regexp is a way to specify conditions for your
+search, and they can be very complex, and equally they can be very
+powerful. If you are unfamiliar with regular expressions, you can
+choose <guilabel>Edit Regular Expression</guilabel> to open
+&kregexpeditor;. This tool allows you to construct your set of
+conditions graphically, and then generates the expression for
+you.</para>
+
+<para>&kregexpeditor; is a very useful tool, and can be used from within
+many &kde; applications other than &rekonq;. You can find more
+information from within its own help file.</para>
+</listitem>
+</varlistentry>
+
+<!-- TODO: "Search metainfo sections" -->
+
+</variablelist>
+
+</sect1>
+
+<sect1 id="kfind-advanced">
+<title>The Properties Tab</title>
+
+<para>
+Here you can refine your search. These are the special refinements
+you can choose:
+</para>
+
+<variablelist>
+
+<varlistentry>
+<term><guilabel>Find all files created or modified</guilabel></term>
+<listitem>
+<para>
+Here you can either enter two dates, between which the
+files were created or modified, or specify a time period.
+</para>
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term><guilabel>File size is</guilabel></term>
+<listitem>
+<para>Here you can specify if the file has to be at least or as most as
+big as the size you entered in the following box.
+</para>
+</listitem>
+</varlistentry>
+
+<varlistentry>
+<term><guilabel>Files owned by user, Files owned by group</guilabel></term>
+<listitem>
+<para>Here you can specify user and group names.
+</para>
+</listitem>
+</varlistentry>
+
+</variablelist>
+
+</sect1>
+
+</chapter>
+
+<!-- ================== CHAPTER ================== -->
+
+<chapter id="credits">
+
+<title>Credits and License</title>
+
+<para>
+&rekonq;
+</para>
+
+<para>
+Program copyright:
+</para>
+
+<itemizedlist>
+<title>Developers</title>
+<listitem>
+<para>&Andrea.Diamantini; &Andrea.Diamantini.mail;</para>
+</listitem>
+
+</itemizedlist>
+
+<para>
+Documentation copyright 2008 &Andrea.Diamantini; &Andrea.Diamantini.mail;
+</para>
+
+<!-- TRANS:CREDIT_FOR_TRANSLATORS -->
+
+&underFDL; <!-- FDL: do not remove -->
+&underBSDLicense; <!-- BSD License -->
+
+</chapter>
+
+<appendix id="installation">
+<title>Installation</title>
+
+<sect1 id="getting-kfind">
+<title>How to obtain &rekonq;</title>
+
+&install.intro.documentation;
+
+</sect1>
+
+<sect1 id="requirements">
+<title>Requirements</title>
+
+<para>
+In order to successfully use &rekonq;, you need at least Qt 4.4.x and &kde; 4.1.x.
+</para>
+
+</sect1>
+
+<sect1 id="compilation">
+<title>Compilation and Installation</title>
+
+&install.compile.documentation;
+
+</sect1>
+
+</appendix>
+
+&documentation.index;
+
+</book>
diff --git a/icons/CMakeLists.txt b/icons/CMakeLists.txt
new file mode 100644
index 00000000..9d7ead58
--- /dev/null
+++ b/icons/CMakeLists.txt
@@ -0,0 +1,2 @@
+# install standard icons
+KDE4_INSTALL_ICONS( ${ICON_INSTALL_DIR} )
diff --git a/icons/hi16-app-rekonq.png b/icons/hi16-app-rekonq.png
new file mode 100644
index 00000000..2427ffef
--- /dev/null
+++ b/icons/hi16-app-rekonq.png
Binary files differ
diff --git a/icons/hi32-app-rekonq.png b/icons/hi32-app-rekonq.png
new file mode 100644
index 00000000..110c6017
--- /dev/null
+++ b/icons/hi32-app-rekonq.png
Binary files differ
diff --git a/icons/hi64-app-rekonq.png b/icons/hi64-app-rekonq.png
new file mode 100644
index 00000000..74d350a5
--- /dev/null
+++ b/icons/hi64-app-rekonq.png
Binary files differ
diff --git a/po/CMakeLists.txt b/po/CMakeLists.txt
new file mode 100644
index 00000000..261e9e4c
--- /dev/null
+++ b/po/CMakeLists.txt
@@ -0,0 +1,34 @@
+FIND_PROGRAM(GETTEXT_MSGFMT_EXECUTABLE msgfmt)
+
+IF(NOT GETTEXT_MSGFMT_EXECUTABLE)
+ MESSAGE(
+"------
+ NOTE: msgfmt not found. Translations will *not* be installed
+------")
+ELSE(NOT GETTEXT_MSGFMT_EXECUTABLE)
+
+ SET(catalogname rekonq)
+
+ ADD_CUSTOM_TARGET(translations ALL)
+
+ FILE(GLOB PO_FILES ${catalogname}*.po)
+
+ FOREACH(_poFile ${PO_FILES})
+ GET_FILENAME_COMPONENT(_poFileName ${_poFile} NAME)
+ STRING(REGEX REPLACE "^${catalogname}_?" "" _langCode ${_poFileName} )
+ STRING(REGEX REPLACE "\\.po$" "" _langCode ${_langCode} )
+
+ IF( _langCode )
+ GET_FILENAME_COMPONENT(_lang ${_poFile} NAME_WE)
+ SET(_gmoFile ${CMAKE_CURRENT_BINARY_DIR}/${_lang}.gmo)
+
+ ADD_CUSTOM_COMMAND(TARGET translations
+ COMMAND ${GETTEXT_MSGFMT_EXECUTABLE} --check -o ${_gmoFile} ${_poFile}
+ DEPENDS ${_poFile})
+ INSTALL(FILES ${_gmoFile} DESTINATION ${LOCALE_INSTALL_DIR}/${_langCode}/LC_MESSAGES/ RENAME ${catalogname}.mo)
+ ENDIF( _langCode )
+
+ ENDFOREACH(_poFile ${PO_FILES})
+
+ENDIF(NOT GETTEXT_MSGFMT_EXECUTABLE)
+
diff --git a/po/rekonq.pot b/po/rekonq.pot
new file mode 100644
index 00000000..986af602
--- /dev/null
+++ b/po/rekonq.pot
@@ -0,0 +1,1007 @@
+# SOME DESCRIPTIVE TITLE.
+# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
+# This file is distributed under the same license as the PACKAGE package.
+# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
+#
+#, fuzzy
+msgid ""
+msgstr ""
+"Project-Id-Version: PACKAGE VERSION\n"
+"Report-Msgid-Bugs-To: http://sourceforge.net/tracker/?"
+"group_id=252277&atid=1126949\n"
+"POT-Creation-Date: 2009-05-02 02:35+0200\n"
+"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
+"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
+"Language-Team: LANGUAGE <LL@li.org>\n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=CHARSET\n"
+"Content-Transfer-Encoding: 8bit\n"
+"Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
+
+#. i18n: file: rekonqui.rc:58
+#. i18n: ectx: Menu (go)
+#: bookmarks.cpp:265 rc.cpp:90
+msgid "&Bookmarks"
+msgstr ""
+
+#: bookmarks.cpp:274
+msgid "Bookmarks Bar"
+msgstr ""
+
+#: cookiejar.cpp:457 cookiejar.cpp:636
+msgid "Website"
+msgstr ""
+
+#: cookiejar.cpp:459
+msgid "Name"
+msgstr ""
+
+#: cookiejar.cpp:461
+msgid "Path"
+msgstr ""
+
+#: cookiejar.cpp:463
+msgid "Secure"
+msgstr ""
+
+#: cookiejar.cpp:465
+msgid "Expires"
+msgstr ""
+
+#: cookiejar.cpp:467
+msgid "Contents"
+msgstr ""
+
+#: cookiejar.cpp:638
+msgid "Status"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:77
+#. i18n: ectx: property (text), widget (QPushButton, allowButton)
+#: cookiejar.cpp:663 rc.cpp:27
+msgid "Allow"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:57
+#. i18n: ectx: property (text), widget (QPushButton, blockButton)
+#: cookiejar.cpp:674 rc.cpp:21
+msgid "Block"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:67
+#. i18n: ectx: property (text), widget (QPushButton, allowForSessionButton)
+#: cookiejar.cpp:685 rc.cpp:24
+msgid "Allow For Session"
+msgstr ""
+
+#: download.cpp:73
+msgid ""
+"Download '%1'?\n"
+"Type: %2"
+msgstr ""
+
+#: download.cpp:74
+msgid "Download '%1'..."
+msgstr ""
+
+#: findbar.cpp:39
+msgid "&Match case"
+msgstr ""
+
+#: findbar.cpp:55
+msgid "Find: "
+msgstr ""
+
+#: findbar.cpp:65
+msgid "&Next"
+msgstr ""
+
+#: findbar.cpp:66
+msgid "&Previous"
+msgstr ""
+
+#: history.cpp:445
+msgid "Title"
+msgstr ""
+
+#: history.cpp:446
+msgid "Address"
+msgstr ""
+
+#: history.cpp:703
+msgid "Show All History"
+msgstr ""
+
+#: history.cpp:707
+msgid "Clear History"
+msgstr ""
+
+#: history.cpp:788
+msgid "Open"
+msgstr ""
+
+#: history.cpp:790
+msgid "Copy"
+msgstr ""
+
+#: history.cpp:792
+msgid "Delete"
+msgstr ""
+
+#: history.cpp:1175
+msgid "Earlier Today"
+msgstr ""
+
+#: history.cpp:1180
+msgid "1 item"
+msgid_plural "%1 items"
+msgstr[0] ""
+msgstr[1] ""
+
+#: main.cpp:29
+msgid "KDE Browser Webkit Based"
+msgstr ""
+
+#: main.cpp:39
+msgid "rekonq"
+msgstr ""
+
+#: main.cpp:43
+msgid "(C) 2008-2009 Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:50
+msgid "Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:51
+msgid "Project Lead, Developer, Italian translations"
+msgstr ""
+
+#: main.cpp:55
+msgid "Domrachev Alexandr"
+msgstr ""
+
+#: main.cpp:56
+msgid "Developer, Russian translations"
+msgstr ""
+
+#: main.cpp:60
+msgid "Pawel Prazak"
+msgstr ""
+
+#: main.cpp:61
+msgid "Developer"
+msgstr ""
+
+#: main.cpp:65
+msgid "Panagiotis Papadopoulos"
+msgstr ""
+
+#: main.cpp:66
+msgid "German translations"
+msgstr ""
+
+#: main.cpp:82
+msgid "Location to open"
+msgstr ""
+
+#: mainview.cpp:98
+msgid "Recently Closed Tabs"
+msgstr ""
+
+#: mainview.cpp:339 mainview.cpp:583
+msgid "(Untitled)"
+msgstr ""
+
+#: mainview.cpp:455
+msgid ""
+"You have modified this page and when closing it you would lose the "
+"modification.\n"
+"Do you really want to close this page?\n"
+msgstr ""
+
+#: mainview.cpp:457
+msgid "Do you really want to close this page?"
+msgstr ""
+
+#: mainview.cpp:514
+msgid "Loading..."
+msgstr ""
+
+#: mainview.cpp:529
+msgid "Loading %1% (%2 %3)..."
+msgstr ""
+
+#: mainview.cpp:556
+msgid "Done"
+msgstr ""
+
+#: mainview.cpp:558
+msgid "Failed to load"
+msgstr ""
+
+#: mainwindow.cpp:177
+msgid "Location Bar"
+msgstr ""
+
+#: mainwindow.cpp:183
+msgid "Search Bar"
+msgstr ""
+
+#: mainwindow.cpp:215 mainwindow.cpp:230 mainwindow.cpp:809
+msgid "Reload"
+msgstr ""
+
+#: mainwindow.cpp:224
+msgid "&Stop"
+msgstr ""
+
+#: mainwindow.cpp:235
+msgid "Open Location"
+msgstr ""
+
+#: mainwindow.cpp:240
+msgid "&Enlarge Font"
+msgstr ""
+
+#: mainwindow.cpp:245
+msgid "&Normal Font"
+msgstr ""
+
+#: mainwindow.cpp:250
+msgid "&Shrink Font"
+msgstr ""
+
+#: mainwindow.cpp:255
+msgid "Page S&ource"
+msgstr ""
+
+#: mainwindow.cpp:260
+msgid "Web &Inspector"
+msgstr ""
+
+#: mainwindow.cpp:265
+msgid "Private &Browsing"
+msgstr ""
+
+#: mainwindow.cpp:271
+msgid "Back"
+msgstr ""
+
+#: mainwindow.cpp:279
+msgid "Forward"
+msgstr ""
+
+#: mainwindow.cpp:284
+msgid "New &Tab"
+msgstr ""
+
+#: mainwindow.cpp:292 tabbar.cpp:110
+msgid "&Close Tab"
+msgstr ""
+
+#: mainwindow.cpp:297
+msgid "Show Next Tab"
+msgstr ""
+
+#: mainwindow.cpp:302
+msgid "Show Previous Tab"
+msgstr ""
+
+#. i18n: file: history.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, HistoryDialog)
+#. i18n: file: settings_privacy.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: mainwindow.cpp:312 mainwindow.cpp:320 rc.cpp:39 rc.cpp:156
+msgid "History"
+msgstr ""
+
+#: mainwindow.cpp:336
+msgid "&History"
+msgstr ""
+
+#: mainwindow.cpp:523
+msgid "Web Resources (*.html *.htm *.svg *.png *.gif *.svgz); All files (*.*)"
+msgstr ""
+
+#: mainwindow.cpp:525
+msgid "Open Web Resource"
+msgstr ""
+
+#: mainwindow.cpp:571
+msgid "Are you sure you want to turn on private browsing?"
+msgstr ""
+
+#: mainwindow.cpp:572
+msgid ""
+"</b><br><br>When private browsing in turned on, webpages are not added to "
+"the history, new cookies are not stored, current cookies cannot be accessed, "
+"site icons will not be stored, session will not be saved, and searches are "
+"not addded to the pop-up menu in the Google search box. Until you close the "
+"window, you can still click the Back and Forward buttons to return to the "
+"webpages you have opened."
+msgstr ""
+
+#: mainwindow.cpp:632 mainwindow.cpp:654
+msgid " not found."
+msgstr ""
+
+#: mainwindow.cpp:766
+msgid ""
+"The web inspector will only work correctly for pages that were loaded after "
+"enabling.\n"
+"Do you want to reload all pages?"
+msgstr ""
+
+#: mainwindow.cpp:768
+msgid "Web Inspector"
+msgstr ""
+
+#: mainwindow.cpp:800
+msgid "Stop loading the current page"
+msgstr ""
+
+#: mainwindow.cpp:801
+msgid "Stop"
+msgstr ""
+
+#: mainwindow.cpp:808
+msgid "Reload the current page"
+msgstr ""
+
+#: mainwindow.cpp:892
+msgid ""
+"Are you sure you want to close the window?\n"
+"You have 1 tap open"
+msgid_plural ""
+"Are you sure you want to close the window?\n"
+"You have %1 tabs open"
+msgstr[0] ""
+msgstr[1] ""
+
+#: mainwindow.cpp:893
+msgid "Are you sure you want to close the window?"
+msgstr ""
+
+#: mainwindow.cpp:895
+msgid "C&lose Current Tab"
+msgstr ""
+
+#: networkaccessmanager.cpp:112
+msgid "<qt>Enter username and password for "
+msgstr ""
+
+#: networkaccessmanager.cpp:113
+msgid " at "
+msgstr ""
+
+#: networkaccessmanager.cpp:140
+msgid "<qt>Connect to proxy "
+msgstr ""
+
+#: networkaccessmanager.cpp:140
+msgid " using:</qt>"
+msgstr ""
+
+#: networkaccessmanager.cpp:160
+msgid ""
+"SSL Errors:\n"
+"\n"
+msgstr ""
+
+#: panelhistory.cpp:50
+msgid "Search: "
+msgstr ""
+
+#: searchbar.cpp:55
+msgid "Search.."
+msgstr ""
+
+#. i18n: file: settings_general.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, general)
+#: settings.cpp:81 rc.cpp:126
+msgid "General"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: settings.cpp:87 rc.cpp:111
+msgid "Fonts"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, privacy)
+#: settings.cpp:93 rc.cpp:153
+msgid "Privacy"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:13
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxy)
+#: settings.cpp:99 rc.cpp:213
+msgid "Proxy"
+msgstr ""
+
+#: settings.cpp:105
+msgid "Webkit"
+msgstr ""
+
+#: settings.cpp:121
+msgid "rekonfig.."
+msgstr ""
+
+#: settings.cpp:143
+msgid "Specifies whether images are automatically loaded in web pages"
+msgstr ""
+
+#: settings.cpp:144
+msgid "Enables the running of JavaScript programs."
+msgstr ""
+
+#: settings.cpp:145
+msgid "Enables Java applets."
+msgstr ""
+
+#: settings.cpp:146
+msgid "Enables plugins in web pages."
+msgstr ""
+
+#: settings.cpp:147
+msgid "Allows JavaScript programs to opening new windows."
+msgstr ""
+
+#: settings.cpp:148
+msgid "Allows JavaScript programs to reading/writing to the clipboard."
+msgstr ""
+
+#: settings.cpp:149
+msgid "Includes hyperlinks in the keyboard focus chain."
+msgstr ""
+
+#: settings.cpp:150
+msgid "Applies the zoom factor on a frame to only the text or all content."
+msgstr ""
+
+#: settings.cpp:151
+msgid "Draws also background color and images when the page is printed."
+msgstr ""
+
+#: settings.cpp:152
+msgid "Support for the HTML 5 offline storage feature."
+msgstr ""
+
+#: settings.cpp:153
+msgid "Support for the HTML 5 web application cache feature."
+msgstr ""
+
+#: settings.cpp:154
+msgid "Support for the HTML 5 local storage feature."
+msgstr ""
+
+#: tabbar.cpp:108
+msgid "Clone Tab"
+msgstr ""
+
+#: tabbar.cpp:111
+msgid "Close &Other Tabs"
+msgstr ""
+
+#: tabbar.cpp:113
+msgid "Reload Tab"
+msgstr ""
+
+#: tabbar.cpp:119
+msgid "Reload All Tabs"
+msgstr ""
+
+#: webview.cpp:245
+msgid "Error loading page: "
+msgstr ""
+
+#: webview.cpp:309
+msgid "Open Link in New &Tab"
+msgstr ""
+
+#: webview.cpp:315
+msgid "Cu&t"
+msgstr ""
+
+#: webview.cpp:320
+msgid "&Copy"
+msgstr ""
+
+#: webview.cpp:325
+msgid "&Paste"
+msgstr ""
+
+#: webview.cpp:330
+msgid "&Save Image As..."
+msgstr ""
+
+#: webview.cpp:335
+msgid "&Copy This Image"
+msgstr ""
+
+#: webview.cpp:340
+msgid "&Save Link As..."
+msgstr ""
+
+#: webview.cpp:345
+msgid "&Copy Link Location"
+msgstr ""
+
+#: webview.cpp:350
+msgid "&Inspect Element"
+msgstr ""
+
+#: webview.cpp:364
+msgid "Bookmark This Page"
+msgstr ""
+
+#: webview.cpp:417
+msgid "&Bookmark This Link"
+msgstr ""
+
+#. i18n: file: cookies.ui:14
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesDialog)
+#. i18n: file: settings_privacy.ui:73
+#. i18n: ectx: property (title), widget (QGroupBox, cookiesGroupBox)
+#: rc.cpp:3 rc.cpp:180
+msgid "Cookies"
+msgstr ""
+
+#. i18n: file: cookies.ui:41
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: cookiesexceptions.ui:114
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: history.ui:40
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#: rc.cpp:6 rc.cpp:33 rc.cpp:42
+msgid "&Remove"
+msgstr ""
+
+#. i18n: file: cookies.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:9
+msgid "Remove &All Cookies"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesExceptionsDialog)
+#: rc.cpp:12
+msgid "Cookie Exceptions"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:19
+#. i18n: ectx: property (title), widget (QGroupBox, newExceptionGroupBox)
+#: rc.cpp:15
+msgid "New Exception"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:27
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:18
+msgid "Domain:"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:89
+#. i18n: ectx: property (title), widget (QGroupBox, ExceptionsGroupBox)
+#: rc.cpp:30
+msgid "Exceptions"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:121
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#. i18n: file: history.ui:47
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:36 rc.cpp:45
+msgid "Remove &All"
+msgstr ""
+
+#. i18n: file: password.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, passwordWidget)
+#. i18n: file: proxy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxyWidget)
+#. i18n: file: settings_webkit.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, webkit)
+#: rc.cpp:48 rc.cpp:63 rc.cpp:243
+msgid "Form"
+msgstr ""
+
+#. i18n: file: password.ui:22
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:51
+msgid "DUMMY ICON"
+msgstr ""
+
+#. i18n: file: password.ui:35
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:54
+msgid "INTRO TEXT DUMMY"
+msgstr ""
+
+#. i18n: file: password.ui:44
+#. i18n: ectx: property (text), widget (QLabel, label)
+#. i18n: file: proxy.ui:37
+#. i18n: ectx: property (text), widget (QLabel, usernameLabel)
+#. i18n: file: settings_proxy.ui:102
+#. i18n: ectx: property (text), widget (QLabel, label_12)
+#: rc.cpp:57 rc.cpp:72 rc.cpp:237
+msgid "Username:"
+msgstr ""
+
+#. i18n: file: password.ui:54
+#. i18n: ectx: property (text), widget (QLabel, lblPassword)
+#. i18n: file: proxy.ui:47
+#. i18n: ectx: property (text), widget (QLabel, passwordLabel)
+#. i18n: file: settings_proxy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label_13)
+#: rc.cpp:60 rc.cpp:75 rc.cpp:240
+msgid "Password:"
+msgstr ""
+
+#. i18n: file: proxy.ui:20
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:66
+msgid "ICON"
+msgstr ""
+
+#. i18n: file: proxy.ui:27
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:69
+msgid "Connect to proxy"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:8
+#. i18n: ectx: Menu (file)
+#: rc.cpp:78
+msgid "&File"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:24
+#. i18n: ectx: Menu (edit)
+#: rc.cpp:81
+msgid "&Edit"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:38
+#. i18n: ectx: Menu (view)
+#: rc.cpp:84
+msgid "&View"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:54
+#. i18n: ectx: Menu (go)
+#: rc.cpp:87
+msgid "Hi&story"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:62
+#. i18n: ectx: Menu (tools)
+#: rc.cpp:93
+msgid "&Tools"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:68
+#. i18n: ectx: Menu (settings)
+#: rc.cpp:96
+msgid "&Settings"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:73
+#. i18n: ectx: Menu (side_panels)
+#: rc.cpp:99
+msgid "Side &Panels"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:88
+#. i18n: ectx: ToolBar (mainToolBar)
+#: rc.cpp:102
+msgid "Main Toolbar"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:100
+#. i18n: ectx: ToolBar (bookmarksToolBar)
+#: rc.cpp:105
+msgid "Bookmark Toolbar"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, fonts)
+#: rc.cpp:108
+msgid "Appearance"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:28
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:114
+msgid "Standard Font"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:35
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:117
+msgid "Fixed Font"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:53
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: rc.cpp:120
+msgid "Dimension"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:61
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:123
+msgid "Font Size"
+msgstr ""
+
+#. i18n: file: settings_general.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:129
+msgid "Places"
+msgstr ""
+
+#. i18n: file: settings_general.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:132
+msgid "Home Page:"
+msgstr ""
+
+#. i18n: file: settings_general.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, setHomeToCurrentPageButton)
+#: rc.cpp:135
+msgid "Set to current page"
+msgstr ""
+
+#. i18n: file: settings_general.ui:73
+#. i18n: ectx: property (text), widget (QLabel, label_7)
+#: rc.cpp:138
+msgid "Save downloads to:"
+msgstr ""
+
+#. i18n: file: settings_general.ui:83
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_downloadToDefaultDir)
+#: rc.cpp:141
+msgid "ask where saving downloads"
+msgstr ""
+
+#. i18n: file: settings_general.ui:93
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_3)
+#: rc.cpp:144
+msgid "Tabbed Browsing"
+msgstr ""
+
+#. i18n: file: settings_general.ui:99
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_alwaysShowTabBar)
+#: rc.cpp:147
+msgid "Always show tab bar"
+msgstr ""
+
+#. i18n: file: settings_general.ui:106
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_openTabsBack)
+#: rc.cpp:150
+msgid "Open tabs in the background"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_4)
+#: rc.cpp:159
+msgid "Remove history items:"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:37
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:162
+msgid "After one day"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:42
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:165
+msgid "After one week"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:47
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:168
+msgid "After two weeks"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:52
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:171
+msgid "After one month"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:57
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:174
+msgid "After one year"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:62
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:177
+msgid "Manually"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:79
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:183
+msgid "Accept Cookies:"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:90
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:186
+msgid "Always"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:95
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:189
+msgid "Never"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:100
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:192
+msgid "Only from sites you visit"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:108
+#. i18n: ectx: property (text), widget (QPushButton, exceptionsButton)
+#: rc.cpp:195
+msgid "Exceptions..."
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:198
+msgid "Keep until:"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:126
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:201
+msgid "They expire"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:131
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:204
+msgid "I exit the application"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:136
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:207
+msgid "At most 90 days"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:144
+#. i18n: ectx: property (text), widget (QPushButton, cookiesButton)
+#: rc.cpp:210
+msgid "Cookies..."
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:19
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_isProxyEnabled)
+#: rc.cpp:216
+msgid "Enable proxy"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:26
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:219
+msgid "Proxy Settings"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:32
+#. i18n: ectx: property (text), widget (QLabel, label_9)
+#: rc.cpp:222
+msgid "Type:"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:43
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:225
+msgid "SOCKS 5"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:48
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:228
+msgid "HTTP"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:56
+#. i18n: ectx: property (text), widget (QLabel, label_10)
+#: rc.cpp:231
+msgid "Host:"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:69
+#. i18n: ectx: property (text), widget (QLabel, label_11)
+#: rc.cpp:234
+msgid "Port:"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:246
+msgid "WebKit Settings"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:26
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_autoLoadImages)
+#: rc.cpp:249
+msgid "Auto Load Images"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:40
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_linksIncludedInFocusChain)
+#: rc.cpp:252
+msgid "Links included in focus chain"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:47
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptEnabled)
+#: rc.cpp:255
+msgid "Javascript support"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:54
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_zoomTextOnly)
+#: rc.cpp:258
+msgid "Zoom Text Only"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:61
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javaEnabled)
+#: rc.cpp:261
+msgid "Java support"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:68
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_printElementBackgrounds)
+#: rc.cpp:264
+msgid "Print element Backgrounds"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:75
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_pluginsEnabled)
+#: rc.cpp:267
+msgid "Plugins"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:82
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineStorageDatabaseEnabled)
+#: rc.cpp:270
+msgid "Offline storage Database"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:89
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanOpenWindows)
+#: rc.cpp:273
+msgid "Javascript can open windows"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:96
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineWebApplicationCacheEnabled)
+#: rc.cpp:276
+msgid "Offline Web Application Cache "
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:103
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanAccessClipboard)
+#: rc.cpp:279
+msgid "Javascript can access clipboard"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:110
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_localStorageDatabaseEnabled)
+#: rc.cpp:282
+msgid "Local storage database"
+msgstr ""
diff --git a/po/rekonq_de.po b/po/rekonq_de.po
new file mode 100644
index 00000000..f5bb5bab
--- /dev/null
+++ b/po/rekonq_de.po
@@ -0,0 +1,1099 @@
+# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
+# This file is distributed under the same license as the rekonq package.
+# FIRST AUTHOR Panagiotis Papadopoulos <pano_90@gmx.net>, 2009.
+msgid ""
+msgstr ""
+"Project-Id-Version: \n"
+"Report-Msgid-Bugs-To: http://sourceforge.net/tracker/?"
+"group_id=252277&atid=1126949\n"
+"POT-Creation-Date: 2009-05-02 02:35+0200\n"
+"PO-Revision-Date: 2009-04-17 23:12+0200\n"
+"Last-Translator: Panagiotis Papadopoulos <pano_90@gmx.net>\n"
+"Language-Team: German <kde-i18n-de@kde.org>\n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Language: de_DE\n"
+"X-Generator: Lokalize 0.3\n"
+"Plural-Forms: nplurals=2; plural=n != 1;\n"
+
+#. i18n: file: rekonqui.rc:58
+#. i18n: ectx: Menu (go)
+#: bookmarks.cpp:265 rc.cpp:90
+msgid "&Bookmarks"
+msgstr "&Lesezeichen"
+
+#: bookmarks.cpp:274
+msgid "Bookmarks Bar"
+msgstr "Lesezeichenleiste"
+
+#: cookiejar.cpp:457 cookiejar.cpp:636
+msgid "Website"
+msgstr "Webseite"
+
+#: cookiejar.cpp:459
+msgid "Name"
+msgstr "Name"
+
+#: cookiejar.cpp:461
+msgid "Path"
+msgstr "Pfad"
+
+#: cookiejar.cpp:463
+msgid "Secure"
+msgstr "Sicher"
+
+#: cookiejar.cpp:465
+msgid "Expires"
+msgstr "Läuft ab am"
+
+#: cookiejar.cpp:467
+msgid "Contents"
+msgstr "Inhalt"
+
+#: cookiejar.cpp:638
+msgid "Status"
+msgstr "Status"
+
+#. i18n: file: cookiesexceptions.ui:77
+#. i18n: ectx: property (text), widget (QPushButton, allowButton)
+#: cookiejar.cpp:663 rc.cpp:27
+msgid "Allow"
+msgstr "Annehmen"
+
+#. i18n: file: cookiesexceptions.ui:57
+#. i18n: ectx: property (text), widget (QPushButton, blockButton)
+#: cookiejar.cpp:674 rc.cpp:21
+msgid "Block"
+msgstr "Zurückweisen"
+
+#. i18n: file: cookiesexceptions.ui:67
+#. i18n: ectx: property (text), widget (QPushButton, allowForSessionButton)
+#: cookiejar.cpp:685 rc.cpp:24
+msgid "Allow For Session"
+msgstr "Für Sitzung annehmen"
+
+#: download.cpp:73
+msgid ""
+"Download '%1'?\n"
+"Type: %2"
+msgstr ""
+
+#: download.cpp:74
+#, fuzzy
+msgid "Download '%1'..."
+msgstr "Download '%1'..."
+
+#: findbar.cpp:39
+msgid "&Match case"
+msgstr "Groß-/Kleinschreibung beachten"
+
+#: findbar.cpp:55
+msgid "Find: "
+msgstr "Suchen:"
+
+#: findbar.cpp:65
+msgid "&Next"
+msgstr "Weiter"
+
+#: findbar.cpp:66
+msgid "&Previous"
+msgstr "Zurück"
+
+#: history.cpp:445
+msgid "Title"
+msgstr "Name"
+
+#: history.cpp:446
+msgid "Address"
+msgstr "Adresse"
+
+#: history.cpp:703
+msgid "Show All History"
+msgstr "Gesamten Verlauf anzeigen"
+
+#: history.cpp:707
+msgid "Clear History"
+msgstr "Verlauf löschen"
+
+#: history.cpp:788
+msgid "Open"
+msgstr "Öffnen"
+
+#: history.cpp:790
+msgid "Copy"
+msgstr "Kopieren"
+
+#: history.cpp:792
+msgid "Delete"
+msgstr "Löschen"
+
+#: history.cpp:1175
+msgid "Earlier Today"
+msgstr ""
+
+#: history.cpp:1180
+msgid "1 item"
+msgid_plural "%1 items"
+msgstr[0] ""
+msgstr[1] ""
+
+#: main.cpp:29
+msgid "KDE Browser Webkit Based"
+msgstr ""
+
+#: main.cpp:39
+msgid "rekonq"
+msgstr "rekonq"
+
+#: main.cpp:43
+#, fuzzy
+msgid "(C) 2008-2009 Andrea Diamantini"
+msgstr "(C) 2008 Andrea Diamantini"
+
+#: main.cpp:50
+msgid "Andrea Diamantini"
+msgstr "Andrea Diamantini"
+
+#: main.cpp:51
+msgid "Project Lead, Developer, Italian translations"
+msgstr ""
+
+#: main.cpp:55
+msgid "Domrachev Alexandr"
+msgstr "Domrachev Alexandr"
+
+#: main.cpp:56
+msgid "Developer, Russian translations"
+msgstr ""
+
+#: main.cpp:60
+#, fuzzy
+msgid "Pawel Prazak"
+msgstr "Paweł Prażak"
+
+#: main.cpp:61
+msgid "Developer"
+msgstr ""
+
+#: main.cpp:65
+msgid "Panagiotis Papadopoulos"
+msgstr ""
+
+#: main.cpp:66
+msgid "German translations"
+msgstr ""
+
+#: main.cpp:82
+msgid "Location to open"
+msgstr ""
+
+#: mainview.cpp:98
+msgid "Recently Closed Tabs"
+msgstr "Geschlossene Unterfenster"
+
+#: mainview.cpp:339 mainview.cpp:583
+msgid "(Untitled)"
+msgstr "(Unbennant)"
+
+#: mainview.cpp:455
+msgid ""
+"You have modified this page and when closing it you would lose the "
+"modification.\n"
+"Do you really want to close this page?\n"
+msgstr ""
+
+#: mainview.cpp:457
+msgid "Do you really want to close this page?"
+msgstr ""
+
+#: mainview.cpp:514
+msgid "Loading..."
+msgstr "Lade ..."
+
+#: mainview.cpp:529
+msgid "Loading %1% (%2 %3)..."
+msgstr "Lade %1% (%2 %3) ..."
+
+#: mainview.cpp:556
+msgid "Done"
+msgstr ""
+
+#: mainview.cpp:558
+msgid "Failed to load"
+msgstr "Laden fehlgeschlagen"
+
+#: mainwindow.cpp:177
+msgid "Location Bar"
+msgstr "Adressleiste"
+
+#: mainwindow.cpp:183
+msgid "Search Bar"
+msgstr "Suchleiste"
+
+#: mainwindow.cpp:215 mainwindow.cpp:230 mainwindow.cpp:809
+#, fuzzy
+msgid "Reload"
+msgstr "Unterfenster neu laden"
+
+#: mainwindow.cpp:224
+msgid "&Stop"
+msgstr "&Stopp"
+
+#: mainwindow.cpp:235
+msgid "Open Location"
+msgstr "Adresse aufrufen"
+
+#: mainwindow.cpp:240
+msgid "&Enlarge Font"
+msgstr "Schrift vergrößern"
+
+#: mainwindow.cpp:245
+msgid "&Normal Font"
+msgstr ""
+
+#: mainwindow.cpp:250
+msgid "&Shrink Font"
+msgstr "Schrift verkleinern"
+
+#: mainwindow.cpp:255
+msgid "Page S&ource"
+msgstr "Seitenquelltext"
+
+#: mainwindow.cpp:260
+msgid "Web &Inspector"
+msgstr ""
+
+#: mainwindow.cpp:265
+msgid "Private &Browsing"
+msgstr ""
+
+#: mainwindow.cpp:271
+msgid "Back"
+msgstr "Zurück"
+
+#: mainwindow.cpp:279
+msgid "Forward"
+msgstr "Nach Vorne"
+
+#: mainwindow.cpp:284
+msgid "New &Tab"
+msgstr "Neues Unterfenster"
+
+#: mainwindow.cpp:292 tabbar.cpp:110
+msgid "&Close Tab"
+msgstr "Unterfenster schließen"
+
+#: mainwindow.cpp:297
+msgid "Show Next Tab"
+msgstr "Nächstes Unterfenster aktivieren"
+
+#: mainwindow.cpp:302
+msgid "Show Previous Tab"
+msgstr "Vorheriges Unterfenster aktivieren"
+
+#. i18n: file: history.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, HistoryDialog)
+#. i18n: file: settings_privacy.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: mainwindow.cpp:312 mainwindow.cpp:320 rc.cpp:39 rc.cpp:156
+msgid "History"
+msgstr "Verlauf"
+
+#: mainwindow.cpp:336
+msgid "&History"
+msgstr "&Verlauf"
+
+#: mainwindow.cpp:523
+#, fuzzy
+msgid "Web Resources (*.html *.htm *.svg *.png *.gif *.svgz); All files (*.*)"
+msgstr "Webinhalte (*.html *.htm *.svg *.png *.gif *.svgz); Alle Dateien(*.*)"
+
+#: mainwindow.cpp:525
+msgid "Open Web Resource"
+msgstr "Webinhalt öffnen"
+
+#: mainwindow.cpp:571
+msgid "Are you sure you want to turn on private browsing?"
+msgstr ""
+
+#: mainwindow.cpp:572
+msgid ""
+"</b><br><br>When private browsing in turned on, webpages are not added to "
+"the history, new cookies are not stored, current cookies cannot be accessed, "
+"site icons will not be stored, session will not be saved, and searches are "
+"not addded to the pop-up menu in the Google search box. Until you close the "
+"window, you can still click the Back and Forward buttons to return to the "
+"webpages you have opened."
+msgstr ""
+
+#: mainwindow.cpp:632 mainwindow.cpp:654
+msgid " not found."
+msgstr ""
+
+#: mainwindow.cpp:766
+msgid ""
+"The web inspector will only work correctly for pages that were loaded after "
+"enabling.\n"
+"Do you want to reload all pages?"
+msgstr ""
+
+#: mainwindow.cpp:768
+msgid "Web Inspector"
+msgstr ""
+
+#: mainwindow.cpp:800
+msgid "Stop loading the current page"
+msgstr ""
+
+#: mainwindow.cpp:801
+msgid "Stop"
+msgstr "Stopp"
+
+#: mainwindow.cpp:808
+msgid "Reload the current page"
+msgstr "Aktuelle Webseite neu laden"
+
+#: mainwindow.cpp:892
+#, fuzzy
+msgid ""
+"Are you sure you want to close the window?\n"
+"You have 1 tap open"
+msgid_plural ""
+"Are you sure you want to close the window?\n"
+"You have %1 tabs open"
+msgstr[0] ""
+"Sind Sie sicher, dass Sie das Fenster schließen wollen?\n"
+"Es sind %1 Unterfenster geöffnet"
+msgstr[1] ""
+"Sind Sie sicher, dass Sie das Fenster schließen wollen?\n"
+"Es sind %1 Unterfenster geöffnet"
+
+#: mainwindow.cpp:893
+msgid "Are you sure you want to close the window?"
+msgstr "Sind Sie sicher, dass Sie das Fenster schließen wollen?"
+
+#: mainwindow.cpp:895
+#, fuzzy
+msgid "C&lose Current Tab"
+msgstr "Unterfenster schließen"
+
+#: networkaccessmanager.cpp:112
+#, fuzzy
+msgid "<qt>Enter username and password for "
+msgstr "<qt>Geben Sie Ihren Benutzernamen und Ihr Passwort ein für "
+
+#: networkaccessmanager.cpp:113
+msgid " at "
+msgstr ""
+
+#: networkaccessmanager.cpp:140
+#, fuzzy
+msgid "<qt>Connect to proxy "
+msgstr "<qt>Zu Proxy verbinden "
+
+#: networkaccessmanager.cpp:140
+msgid " using:</qt>"
+msgstr ""
+
+#: networkaccessmanager.cpp:160
+msgid ""
+"SSL Errors:\n"
+"\n"
+msgstr ""
+"SSL-Fehler:\n"
+"\n"
+
+#: panelhistory.cpp:50
+msgid "Search: "
+msgstr "Suchen:"
+
+#: searchbar.cpp:55
+#, fuzzy
+msgid "Search.."
+msgstr "Suchen ..."
+
+#. i18n: file: settings_general.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, general)
+#: settings.cpp:81 rc.cpp:126
+msgid "General"
+msgstr "Allgemein"
+
+#. i18n: file: settings_fonts.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: settings.cpp:87 rc.cpp:111
+msgid "Fonts"
+msgstr "Schriftarten"
+
+#. i18n: file: settings_privacy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, privacy)
+#: settings.cpp:93 rc.cpp:153
+#, fuzzy
+msgid "Privacy"
+msgstr "Privatsphäre"
+
+#. i18n: file: settings_proxy.ui:13
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxy)
+#: settings.cpp:99 rc.cpp:213
+msgid "Proxy"
+msgstr "Proxy"
+
+#: settings.cpp:105
+#, fuzzy
+msgid "Webkit"
+msgstr "Webseite"
+
+#: settings.cpp:121
+#, fuzzy
+msgid "rekonfig.."
+msgstr "rekonq"
+
+#: settings.cpp:143
+msgid "Specifies whether images are automatically loaded in web pages"
+msgstr ""
+
+#: settings.cpp:144
+msgid "Enables the running of JavaScript programs."
+msgstr ""
+
+#: settings.cpp:145
+#, fuzzy
+msgid "Enables Java applets."
+msgstr "Javascript aktivieren"
+
+#: settings.cpp:146
+#, fuzzy
+msgid "Enables plugins in web pages."
+msgstr "Plugins aktivieren"
+
+#: settings.cpp:147
+msgid "Allows JavaScript programs to opening new windows."
+msgstr ""
+
+#: settings.cpp:148
+msgid "Allows JavaScript programs to reading/writing to the clipboard."
+msgstr ""
+
+#: settings.cpp:149
+msgid "Includes hyperlinks in the keyboard focus chain."
+msgstr ""
+
+#: settings.cpp:150
+msgid "Applies the zoom factor on a frame to only the text or all content."
+msgstr ""
+
+#: settings.cpp:151
+msgid "Draws also background color and images when the page is printed."
+msgstr ""
+
+#: settings.cpp:152
+msgid "Support for the HTML 5 offline storage feature."
+msgstr ""
+
+#: settings.cpp:153
+msgid "Support for the HTML 5 web application cache feature."
+msgstr ""
+
+#: settings.cpp:154
+msgid "Support for the HTML 5 local storage feature."
+msgstr ""
+
+#: tabbar.cpp:108
+msgid "Clone Tab"
+msgstr "Unterfenster duplizieren"
+
+#: tabbar.cpp:111
+msgid "Close &Other Tabs"
+msgstr "Andere Unterfenster schließen"
+
+#: tabbar.cpp:113
+msgid "Reload Tab"
+msgstr "Unterfenster neu laden"
+
+#: tabbar.cpp:119
+msgid "Reload All Tabs"
+msgstr "Alle Unterfenster neu laden"
+
+#: webview.cpp:245
+msgid "Error loading page: "
+msgstr ""
+
+#: webview.cpp:309
+msgid "Open Link in New &Tab"
+msgstr "In neuem Unterfenster öffnen"
+
+#: webview.cpp:315
+msgid "Cu&t"
+msgstr "Ausschneiden"
+
+#: webview.cpp:320
+msgid "&Copy"
+msgstr "&Kopieren"
+
+#: webview.cpp:325
+msgid "&Paste"
+msgstr "&Einfügen"
+
+#: webview.cpp:330
+msgid "&Save Image As..."
+msgstr "Bild speichern unter ..."
+
+#: webview.cpp:335
+msgid "&Copy This Image"
+msgstr "Bild kopieren"
+
+#: webview.cpp:340
+msgid "&Save Link As..."
+msgstr "Verknüpfung speichern unter ..."
+
+#: webview.cpp:345
+msgid "&Copy Link Location"
+msgstr "Verknüpfungsaddresse kopieren"
+
+#: webview.cpp:350
+msgid "&Inspect Element"
+msgstr ""
+
+#: webview.cpp:364
+msgid "Bookmark This Page"
+msgstr "Lesezeichen für diese Seite"
+
+#: webview.cpp:417
+msgid "&Bookmark This Link"
+msgstr "Lesezeichen für diese Verknüpfung"
+
+#. i18n: file: cookies.ui:14
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesDialog)
+#. i18n: file: settings_privacy.ui:73
+#. i18n: ectx: property (title), widget (QGroupBox, cookiesGroupBox)
+#: rc.cpp:3 rc.cpp:180
+msgid "Cookies"
+msgstr "Cookies"
+
+#. i18n: file: cookies.ui:41
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: cookiesexceptions.ui:114
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: history.ui:40
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#: rc.cpp:6 rc.cpp:33 rc.cpp:42
+msgid "&Remove"
+msgstr "Entfernen"
+
+#. i18n: file: cookies.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:9
+msgid "Remove &All Cookies"
+msgstr "Alle Cookies entfernen"
+
+#. i18n: file: cookiesexceptions.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesExceptionsDialog)
+#: rc.cpp:12
+msgid "Cookie Exceptions"
+msgstr "Cookie-Ausnahmen"
+
+#. i18n: file: cookiesexceptions.ui:19
+#. i18n: ectx: property (title), widget (QGroupBox, newExceptionGroupBox)
+#: rc.cpp:15
+msgid "New Exception"
+msgstr "Neue Ausnahme"
+
+#. i18n: file: cookiesexceptions.ui:27
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:18
+#, fuzzy
+msgid "Domain:"
+msgstr "Domain:"
+
+#. i18n: file: cookiesexceptions.ui:89
+#. i18n: ectx: property (title), widget (QGroupBox, ExceptionsGroupBox)
+#: rc.cpp:30
+msgid "Exceptions"
+msgstr "Ausnahmen"
+
+#. i18n: file: cookiesexceptions.ui:121
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#. i18n: file: history.ui:47
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:36 rc.cpp:45
+msgid "Remove &All"
+msgstr "&Alle Entfernen"
+
+#. i18n: file: password.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, passwordWidget)
+#. i18n: file: proxy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxyWidget)
+#. i18n: file: settings_webkit.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, webkit)
+#: rc.cpp:48 rc.cpp:63 rc.cpp:243
+msgid "Form"
+msgstr ""
+
+#. i18n: file: password.ui:22
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:51
+msgid "DUMMY ICON"
+msgstr ""
+
+#. i18n: file: password.ui:35
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:54
+msgid "INTRO TEXT DUMMY"
+msgstr ""
+
+#. i18n: file: password.ui:44
+#. i18n: ectx: property (text), widget (QLabel, label)
+#. i18n: file: proxy.ui:37
+#. i18n: ectx: property (text), widget (QLabel, usernameLabel)
+#. i18n: file: settings_proxy.ui:102
+#. i18n: ectx: property (text), widget (QLabel, label_12)
+#: rc.cpp:57 rc.cpp:72 rc.cpp:237
+msgid "Username:"
+msgstr "Benutzername:"
+
+#. i18n: file: password.ui:54
+#. i18n: ectx: property (text), widget (QLabel, lblPassword)
+#. i18n: file: proxy.ui:47
+#. i18n: ectx: property (text), widget (QLabel, passwordLabel)
+#. i18n: file: settings_proxy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label_13)
+#: rc.cpp:60 rc.cpp:75 rc.cpp:240
+msgid "Password:"
+msgstr "Passwort:"
+
+#. i18n: file: proxy.ui:20
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:66
+msgid "ICON"
+msgstr ""
+
+#. i18n: file: proxy.ui:27
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:69
+#, fuzzy
+msgid "Connect to proxy"
+msgstr "Zu Proxy verbinden"
+
+#. i18n: file: rekonqui.rc:8
+#. i18n: ectx: Menu (file)
+#: rc.cpp:78
+msgid "&File"
+msgstr "&Datei"
+
+#. i18n: file: rekonqui.rc:24
+#. i18n: ectx: Menu (edit)
+#: rc.cpp:81
+msgid "&Edit"
+msgstr "&Bearbeiten"
+
+#. i18n: file: rekonqui.rc:38
+#. i18n: ectx: Menu (view)
+#: rc.cpp:84
+msgid "&View"
+msgstr "&Ansicht"
+
+#. i18n: file: rekonqui.rc:54
+#. i18n: ectx: Menu (go)
+#: rc.cpp:87
+msgid "Hi&story"
+msgstr "Verlauf"
+
+#. i18n: file: rekonqui.rc:62
+#. i18n: ectx: Menu (tools)
+#: rc.cpp:93
+msgid "&Tools"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:68
+#. i18n: ectx: Menu (settings)
+#: rc.cpp:96
+msgid "&Settings"
+msgstr "&Einstellungen"
+
+#. i18n: file: rekonqui.rc:73
+#. i18n: ectx: Menu (side_panels)
+#: rc.cpp:99
+#, fuzzy
+msgid "Side &Panels"
+msgstr "Lesezeichen-Seitenleiste anzeigen"
+
+#. i18n: file: rekonqui.rc:88
+#. i18n: ectx: ToolBar (mainToolBar)
+#: rc.cpp:102
+msgid "Main Toolbar"
+msgstr "Haupt-Werkzeugsleiste"
+
+#. i18n: file: rekonqui.rc:100
+#. i18n: ectx: ToolBar (bookmarksToolBar)
+#: rc.cpp:105
+msgid "Bookmark Toolbar"
+msgstr "Lesezeichen-Werkzeugsleiste"
+
+#. i18n: file: settings_fonts.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, fonts)
+#: rc.cpp:108
+#, fuzzy
+msgid "Appearance"
+msgstr "Erscheinungsbild"
+
+#. i18n: file: settings_fonts.ui:28
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:114
+msgid "Standard Font"
+msgstr "Allgemein"
+
+#. i18n: file: settings_fonts.ui:35
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:117
+msgid "Fixed Font"
+msgstr "Feste Breite"
+
+#. i18n: file: settings_fonts.ui:53
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: rc.cpp:120
+msgid "Dimension"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:61
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:123
+msgid "Font Size"
+msgstr "Schriftgröße"
+
+#. i18n: file: settings_general.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:129
+msgid "Places"
+msgstr "Orte"
+
+#. i18n: file: settings_general.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:132
+#, fuzzy
+msgid "Home Page:"
+msgstr "Startseite:"
+
+#. i18n: file: settings_general.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, setHomeToCurrentPageButton)
+#: rc.cpp:135
+msgid "Set to current page"
+msgstr ""
+
+#. i18n: file: settings_general.ui:73
+#. i18n: ectx: property (text), widget (QLabel, label_7)
+#: rc.cpp:138
+#, fuzzy
+msgid "Save downloads to:"
+msgstr "&Downloads speichern unter:"
+
+#. i18n: file: settings_general.ui:83
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_downloadToDefaultDir)
+#: rc.cpp:141
+msgid "ask where saving downloads"
+msgstr ""
+
+#. i18n: file: settings_general.ui:93
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_3)
+#: rc.cpp:144
+msgid "Tabbed Browsing"
+msgstr ""
+
+#. i18n: file: settings_general.ui:99
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_alwaysShowTabBar)
+#: rc.cpp:147
+#, fuzzy
+msgid "Always show tab bar"
+msgstr "Unterfensterleiste immer anzeigen"
+
+#. i18n: file: settings_general.ui:106
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_openTabsBack)
+#: rc.cpp:150
+msgid "Open tabs in the background"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_4)
+#: rc.cpp:159
+#, fuzzy
+msgid "Remove history items:"
+msgstr "Verlaufseinträge entfernen nach:"
+
+#. i18n: file: settings_privacy.ui:37
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:162
+#, fuzzy
+msgid "After one day"
+msgstr "Einem Tag"
+
+#. i18n: file: settings_privacy.ui:42
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:165
+#, fuzzy
+msgid "After one week"
+msgstr "Einer Woche"
+
+#. i18n: file: settings_privacy.ui:47
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:168
+#, fuzzy
+msgid "After two weeks"
+msgstr "Zwei Wochen"
+
+#. i18n: file: settings_privacy.ui:52
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:171
+#, fuzzy
+msgid "After one month"
+msgstr "Einem Monat"
+
+#. i18n: file: settings_privacy.ui:57
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:174
+#, fuzzy
+msgid "After one year"
+msgstr "Einem Jahr"
+
+#. i18n: file: settings_privacy.ui:62
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:177
+msgid "Manually"
+msgstr "Manuell"
+
+#. i18n: file: settings_privacy.ui:79
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:183
+#, fuzzy
+msgid "Accept Cookies:"
+msgstr "Cookies annehmen:"
+
+#. i18n: file: settings_privacy.ui:90
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:186
+msgid "Always"
+msgstr "Immer"
+
+#. i18n: file: settings_privacy.ui:95
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:189
+msgid "Never"
+msgstr "Nie"
+
+#. i18n: file: settings_privacy.ui:100
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:192
+#, fuzzy
+msgid "Only from sites you visit"
+msgstr "Von besuchten Seiten"
+
+#. i18n: file: settings_privacy.ui:108
+#. i18n: ectx: property (text), widget (QPushButton, exceptionsButton)
+#: rc.cpp:195
+msgid "Exceptions..."
+msgstr "Ausnahmen ..."
+
+#. i18n: file: settings_privacy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:198
+msgid "Keep until:"
+msgstr "Behalten bis:"
+
+#. i18n: file: settings_privacy.ui:126
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:201
+msgid "They expire"
+msgstr "Sie ablaufen"
+
+#. i18n: file: settings_privacy.ui:131
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:204
+#, fuzzy
+msgid "I exit the application"
+msgstr "Die Anwendung geschlossen wird"
+
+#. i18n: file: settings_privacy.ui:136
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:207
+#, fuzzy
+msgid "At most 90 days"
+msgstr "Spätestens 90 Tagen"
+
+#. i18n: file: settings_privacy.ui:144
+#. i18n: ectx: property (text), widget (QPushButton, cookiesButton)
+#: rc.cpp:210
+msgid "Cookies..."
+msgstr "Cookies ..."
+
+#. i18n: file: settings_proxy.ui:19
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_isProxyEnabled)
+#: rc.cpp:216
+msgid "Enable proxy"
+msgstr "Proxy aktivieren"
+
+#. i18n: file: settings_proxy.ui:26
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:219
+msgid "Proxy Settings"
+msgstr "Proxy-Einstellungen"
+
+#. i18n: file: settings_proxy.ui:32
+#. i18n: ectx: property (text), widget (QLabel, label_9)
+#: rc.cpp:222
+msgid "Type:"
+msgstr "Typ:"
+
+#. i18n: file: settings_proxy.ui:43
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:225
+msgid "SOCKS 5"
+msgstr "SOCKS 5"
+
+#. i18n: file: settings_proxy.ui:48
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:228
+msgid "HTTP"
+msgstr "HTTP"
+
+#. i18n: file: settings_proxy.ui:56
+#. i18n: ectx: property (text), widget (QLabel, label_10)
+#: rc.cpp:231
+msgid "Host:"
+msgstr "Rechner:"
+
+#. i18n: file: settings_proxy.ui:69
+#. i18n: ectx: property (text), widget (QLabel, label_11)
+#: rc.cpp:234
+msgid "Port:"
+msgstr "Port:"
+
+#. i18n: file: settings_webkit.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:246
+#, fuzzy
+msgid "WebKit Settings"
+msgstr "&Einstellungen"
+
+#. i18n: file: settings_webkit.ui:26
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_autoLoadImages)
+#: rc.cpp:249
+msgid "Auto Load Images"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:40
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_linksIncludedInFocusChain)
+#: rc.cpp:252
+msgid "Links included in focus chain"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:47
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptEnabled)
+#: rc.cpp:255
+msgid "Javascript support"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:54
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_zoomTextOnly)
+#: rc.cpp:258
+msgid "Zoom Text Only"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:61
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javaEnabled)
+#: rc.cpp:261
+msgid "Java support"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:68
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_printElementBackgrounds)
+#: rc.cpp:264
+msgid "Print element Backgrounds"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:75
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_pluginsEnabled)
+#: rc.cpp:267
+#, fuzzy
+msgid "Plugins"
+msgstr "Plugins aktivieren"
+
+#. i18n: file: settings_webkit.ui:82
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineStorageDatabaseEnabled)
+#: rc.cpp:270
+msgid "Offline storage Database"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:89
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanOpenWindows)
+#: rc.cpp:273
+msgid "Javascript can open windows"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:96
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineWebApplicationCacheEnabled)
+#: rc.cpp:276
+msgid "Offline Web Application Cache "
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:103
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanAccessClipboard)
+#: rc.cpp:279
+msgid "Javascript can access clipboard"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:110
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_localStorageDatabaseEnabled)
+#: rc.cpp:282
+msgid "Local storage database"
+msgstr ""
+
+#~ msgid "Show side panel"
+#~ msgstr "Lesezeichen-Seitenleiste anzeigen"
+
+#~ msgid "Print Document"
+#~ msgstr "Dokument drucken"
+
+#~ msgid "Location Toolbar"
+#~ msgstr "Adressleiste"
+
+#, fuzzy
+#~ msgid "reload"
+#~ msgstr "Unterfenster neu laden"
+
+#, fuzzy
+#~ msgid "Clear Location Bar"
+#~ msgstr "Adressleiste"
+
+#~ msgid "Finished loading"
+#~ msgstr "Laden abgeschlossen"
+
+#~ msgid "Bookmarks"
+#~ msgstr "Lesezeichen"
+
+#~ msgid "Interface"
+#~ msgstr "Oberfläche"
+
+#~ msgid "Downloads"
+#~ msgstr "Downloads"
+
+#~ msgid "Show close button on tabs"
+#~ msgstr "„Schließen“-Knopf auf Unterfenstern anzeigen"
+
+#~ msgid "Confirm when closing window with multiple tabs"
+#~ msgstr ""
+#~ "&Beim Schließen von Fenster mit mehreren Unterfenster, um Bestätigung "
+#~ "fragen"
+
+#~ msgid "Enable location bar progress indication"
+#~ msgstr "Fortschrittsanzeige in Adressleiste aktivieren"
+
+#, fuzzy
+#~ msgid "Secure connection indicator:"
+#~ msgstr "Anzeige einer sicheren Verbindung:"
+
+#~ msgid "Progress indicator:"
+#~ msgstr "Fortschrittsanzeige:"
+
+#~ msgid "Web Content"
+#~ msgstr "Web-Inhalt"
+
+#~ msgid "Ask destination for each download"
+#~ msgstr "Zielort für jeden Download nachfragen"
diff --git a/po/rekonq_it.po b/po/rekonq_it.po
new file mode 100644
index 00000000..d134f727
--- /dev/null
+++ b/po/rekonq_it.po
@@ -0,0 +1,1038 @@
+# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
+# This file is distributed under the same license as the rekonq package.
+# FIRST AUTHOR Andrea Diamantini <adjam7@gmail.com>, 2009.
+msgid ""
+msgstr ""
+"Project-Id-Version: rekonq\n"
+"Report-Msgid-Bugs-To: http://sourceforge."
+"net/tracker/?group_id=252277&atid=1126949\n"
+"POT-Creation-Date: 2009-05-02 02:35+0200\n"
+"PO-Revision-Date: 2009-05-02 02:48+0200\n"
+"Last-Translator: Andrea Diamantini <adjam7@gmail.com>\n"
+"Language-Team: American English <kde-i18n-doc@kde.org>\n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Language: it_IT\n"
+"X-Generator: Lokalize 0.3\n"
+"Plural-Forms: nplurals=2; plural=(n != 1);\n"
+
+#. i18n: file: rekonqui.rc:58
+#. i18n: ectx: Menu (go)
+#: bookmarks.cpp:265 rc.cpp:90
+msgid "&Bookmarks"
+msgstr "B&ookmarks"
+
+#: bookmarks.cpp:274
+msgid "Bookmarks Bar"
+msgstr "B&ookmarks"
+
+#: cookiejar.cpp:457 cookiejar.cpp:636
+msgid "Website"
+msgstr ""
+
+#: cookiejar.cpp:459
+msgid "Name"
+msgstr "Nome"
+
+#: cookiejar.cpp:461
+msgid "Path"
+msgstr "path"
+
+#: cookiejar.cpp:463
+msgid "Secure"
+msgstr ""
+
+#: cookiejar.cpp:465
+msgid "Expires"
+msgstr "Scade"
+
+#: cookiejar.cpp:467
+msgid "Contents"
+msgstr ""
+
+#: cookiejar.cpp:638
+msgid "Status"
+msgstr "Stato"
+
+#. i18n: file: cookiesexceptions.ui:77
+#. i18n: ectx: property (text), widget (QPushButton, allowButton)
+#: cookiejar.cpp:663 rc.cpp:27
+msgid "Allow"
+msgstr "Permetti"
+
+#. i18n: file: cookiesexceptions.ui:57
+#. i18n: ectx: property (text), widget (QPushButton, blockButton)
+#: cookiejar.cpp:674 rc.cpp:21
+msgid "Block"
+msgstr "Blocca"
+
+#. i18n: file: cookiesexceptions.ui:67
+#. i18n: ectx: property (text), widget (QPushButton, allowForSessionButton)
+#: cookiejar.cpp:685 rc.cpp:24
+msgid "Allow For Session"
+msgstr "Permetti per una sessione"
+
+#: download.cpp:73
+msgid ""
+"Download '%1'?\n"
+"Type: %2"
+msgstr ""
+"Download '%1' \n"
+" Tipo: %2"
+
+#: download.cpp:74
+msgid "Download '%1'..."
+msgstr ""
+
+#: findbar.cpp:39
+msgid "&Match case"
+msgstr ""
+
+#: findbar.cpp:55
+msgid "Find: "
+msgstr "Trova:"
+
+#: findbar.cpp:65
+msgid "&Next"
+msgstr ""
+
+#: findbar.cpp:66
+msgid "&Previous"
+msgstr ""
+
+#: history.cpp:445
+msgid "Title"
+msgstr "Titolo"
+
+#: history.cpp:446
+msgid "Address"
+msgstr "Indirizzo"
+
+#: history.cpp:703
+msgid "Show All History"
+msgstr "Mostra la cronologia"
+
+#: history.cpp:707
+msgid "Clear History"
+msgstr "Cancella la cronologia"
+
+#: history.cpp:788
+msgid "Open"
+msgstr "Apri"
+
+#: history.cpp:790
+msgid "Copy"
+msgstr "Copia"
+
+#: history.cpp:792
+msgid "Delete"
+msgstr "Cancella"
+
+#: history.cpp:1175
+msgid "Earlier Today"
+msgstr ""
+
+#: history.cpp:1180
+msgid "1 item"
+msgid_plural "%1 items"
+msgstr[0] ""
+msgstr[1] ""
+
+#: main.cpp:29
+msgid "KDE Browser Webkit Based"
+msgstr ""
+
+#: main.cpp:39
+msgid "rekonq"
+msgstr ""
+
+#: main.cpp:43
+msgid "(C) 2008-2009 Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:50
+msgid "Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:51
+msgid "Project Lead, Developer, Italian translations"
+msgstr ""
+
+#: main.cpp:55
+msgid "Domrachev Alexandr"
+msgstr ""
+
+#: main.cpp:56
+msgid "Developer, Russian translations"
+msgstr ""
+
+#: main.cpp:60
+msgid "Pawel Prazak"
+msgstr ""
+
+#: main.cpp:61
+msgid "Developer"
+msgstr ""
+
+#: main.cpp:65
+msgid "Panagiotis Papadopoulos"
+msgstr ""
+
+#: main.cpp:66
+msgid "German translations"
+msgstr ""
+
+#: main.cpp:82
+msgid "Location to open"
+msgstr "Indirizzo da aprire"
+
+#: mainview.cpp:98
+msgid "Recently Closed Tabs"
+msgstr "tabs chiuse recentemente"
+
+#: mainview.cpp:339 mainview.cpp:583
+msgid "(Untitled)"
+msgstr "(senza titolo)"
+
+#: mainview.cpp:455
+msgid ""
+"You have modified this page and when closing it you would lose the "
+"modification.\n"
+"Do you really want to close this page?\n"
+msgstr ""
+"Hai modificato questa pagina e chiudendola, potresti perdere queste "
+"modifiche.\n"
+"Vuoi davvero chiudere questa pagina?\n"
+
+#: mainview.cpp:457
+msgid "Do you really want to close this page?"
+msgstr "Vuoi davvero chiudere questa pagina?"
+
+#: mainview.cpp:514
+msgid "Loading..."
+msgstr "Sto caricando.. "
+
+#: mainview.cpp:529
+msgid "Loading %1% (%2 %3)..."
+msgstr "Sto caricando %1% (%2 %3)... "
+
+#: mainview.cpp:556
+msgid "Done"
+msgstr "Fatto"
+
+#: mainview.cpp:558
+msgid "Failed to load"
+msgstr "Caricamento fallito"
+
+#: mainwindow.cpp:177
+msgid "Location Bar"
+msgstr "Barra degli Indirizzi"
+
+#: mainwindow.cpp:183
+msgid "Search Bar"
+msgstr "Barra di ricerca"
+
+#: mainwindow.cpp:215 mainwindow.cpp:230 mainwindow.cpp:809
+msgid "Reload"
+msgstr "Ricarica"
+
+#: mainwindow.cpp:224
+msgid "&Stop"
+msgstr "&Stop"
+
+#: mainwindow.cpp:235
+msgid "Open Location"
+msgstr "Carica Indirizzo"
+
+#: mainwindow.cpp:240
+msgid "&Enlarge Font"
+msgstr "Allarga Caratt&ere"
+
+#: mainwindow.cpp:245
+msgid "&Normal Font"
+msgstr "Carattere &Normale"
+
+#: mainwindow.cpp:250
+msgid "&Shrink Font"
+msgstr "&Stringi Carattere"
+
+#: mainwindow.cpp:255
+msgid "Page S&ource"
+msgstr "S&orgente della pagina"
+
+#: mainwindow.cpp:260
+msgid "Web &Inspector"
+msgstr ""
+
+#: mainwindow.cpp:265
+msgid "Private &Browsing"
+msgstr "Navigazione Privata"
+
+#: mainwindow.cpp:271
+msgid "Back"
+msgstr "Indietro"
+
+#: mainwindow.cpp:279
+msgid "Forward"
+msgstr "Avanti"
+
+#: mainwindow.cpp:284
+msgid "New &Tab"
+msgstr "Nuova &Tab"
+
+#: mainwindow.cpp:292 tabbar.cpp:110
+msgid "&Close Tab"
+msgstr "&Chiudi Tab"
+
+#: mainwindow.cpp:297
+msgid "Show Next Tab"
+msgstr "Mostra la prossima Tab"
+
+#: mainwindow.cpp:302
+msgid "Show Previous Tab"
+msgstr "Mostra la Tab precedente"
+
+#. i18n: file: history.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, HistoryDialog)
+#. i18n: file: settings_privacy.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: mainwindow.cpp:312 mainwindow.cpp:320 rc.cpp:39 rc.cpp:156
+msgid "History"
+msgstr "Cronologia"
+
+#: mainwindow.cpp:336
+msgid "&History"
+msgstr "Cronologia"
+
+#: mainwindow.cpp:523
+msgid "Web Resources (*.html *.htm *.svg *.png *.gif *.svgz); All files (*.*)"
+msgstr ""
+"Risorse Web (*.html *.htm *.svg *.png *.gif *.svgz);;Tutti i files (*.*)"
+
+#: mainwindow.cpp:525
+msgid "Open Web Resource"
+msgstr "Apri Risorsa Web"
+
+#: mainwindow.cpp:571
+msgid "Are you sure you want to turn on private browsing?"
+msgstr "Sei sicuro di voler utilizzare la navigazione anonima?"
+
+#: mainwindow.cpp:572
+msgid ""
+"</b><br><br>When private browsing in turned on, webpages are not added to "
+"the history, new cookies are not stored, current cookies cannot be accessed, "
+"site icons will not be stored, session will not be saved, and searches are "
+"not addded to the pop-up menu in the Google search box. Until you close the "
+"window, you can still click the Back and Forward buttons to return to the "
+"webpages you have opened."
+msgstr ""
+
+#: mainwindow.cpp:632 mainwindow.cpp:654
+msgid " not found."
+msgstr "non trovato"
+
+#: mainwindow.cpp:766
+msgid ""
+"The web inspector will only work correctly for pages that were loaded after "
+"enabling.\n"
+"Do you want to reload all pages?"
+msgstr ""
+"Lo web inspector funziona correttamente solo per quelle pagine caricate dopo "
+"averlo abilitato.\n"
+"Vuoi ricaricare tutte le pagine?"
+
+#: mainwindow.cpp:768
+msgid "Web Inspector"
+msgstr ""
+
+#: mainwindow.cpp:800
+msgid "Stop loading the current page"
+msgstr "Ferma il caricamento della pagina corrente"
+
+#: mainwindow.cpp:801
+msgid "Stop"
+msgstr ""
+
+#: mainwindow.cpp:808
+msgid "Reload the current page"
+msgstr "Ricarica la pagina corrente"
+
+#: mainwindow.cpp:892
+msgid ""
+"Are you sure you want to close the window?\n"
+"You have 1 tap open"
+msgid_plural ""
+"Are you sure you want to close the window?\n"
+"You have %1 tabs open"
+msgstr[0] "Vuoi davvero chiudere questa pagina?\n C'è 1 tab aperta"
+msgstr[1] "Vuoi davvero chiudere questa pagina?"
+
+#: mainwindow.cpp:893
+msgid "Are you sure you want to close the window?"
+msgstr "Vuoi davvero chiudere questa pagina?"
+
+#: mainwindow.cpp:895
+msgid "C&lose Current Tab"
+msgstr "&Chiudi la tab corrente"
+
+#: networkaccessmanager.cpp:112
+msgid "<qt>Enter username and password for "
+msgstr "<qt> Inserisci username e password per"
+
+#: networkaccessmanager.cpp:113
+msgid " at "
+msgstr "a"
+
+#: networkaccessmanager.cpp:140
+msgid "<qt>Connect to proxy "
+msgstr "<qt> Connessione al proxy"
+
+#: networkaccessmanager.cpp:140
+msgid " using:</qt>"
+msgstr "utilizzando: </qt> "
+
+#: networkaccessmanager.cpp:160
+msgid ""
+"SSL Errors:\n"
+"\n"
+msgstr ""
+
+#: panelhistory.cpp:50
+msgid "Search: "
+msgstr "Cerca:"
+
+#: searchbar.cpp:55
+msgid "Search.."
+msgstr "Cerca.."
+
+#. i18n: file: settings_general.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, general)
+#: settings.cpp:81 rc.cpp:126
+msgid "General"
+msgstr "Generale"
+
+#. i18n: file: settings_fonts.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: settings.cpp:87 rc.cpp:111
+msgid "Fonts"
+msgstr "Caratteri"
+
+#. i18n: file: settings_privacy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, privacy)
+#: settings.cpp:93 rc.cpp:153
+msgid "Privacy"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:13
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxy)
+#: settings.cpp:99 rc.cpp:213
+msgid "Proxy"
+msgstr ""
+
+#: settings.cpp:105
+msgid "Webkit"
+msgstr ""
+
+#: settings.cpp:121
+msgid "rekonfig.."
+msgstr ""
+
+#: settings.cpp:143
+msgid "Specifies whether images are automatically loaded in web pages"
+msgstr ""
+"Specifica se le immagini vengano caricate automaticamente nelle pagine web"
+
+#: settings.cpp:144
+msgid "Enables the running of JavaScript programs."
+msgstr "Abilita l'esecuzione del javascript"
+
+#: settings.cpp:145
+msgid "Enables Java applets."
+msgstr "Abilita la applet java"
+
+#: settings.cpp:146
+msgid "Enables plugins in web pages."
+msgstr "Abilita i plugins nelle pagine web"
+
+#: settings.cpp:147
+msgid "Allows JavaScript programs to opening new windows."
+msgstr "Permetti al javascript aprire nuove finestre"
+
+#: settings.cpp:148
+msgid "Allows JavaScript programs to reading/writing to the clipboard."
+msgstr "Permetti a javascript to leggere/scrivere nella clipboard"
+
+#: settings.cpp:149
+msgid "Includes hyperlinks in the keyboard focus chain."
+msgstr "Includi link nella sequenza di tab della tastiera"
+
+#: settings.cpp:150
+msgid "Applies the zoom factor on a frame to only the text or all content."
+msgstr ""
+"Applica il fattore di zoom in un frame solo al testo o a tutto il contenuto"
+
+#: settings.cpp:151
+msgid "Draws also background color and images when the page is printed."
+msgstr ""
+"Disegna anche i colori e le immagini di sfondo quando la pagina viene "
+"stampata"
+
+#: settings.cpp:152
+msgid "Support for the HTML 5 offline storage feature."
+msgstr ""
+
+#: settings.cpp:153
+msgid "Support for the HTML 5 web application cache feature."
+msgstr " "
+
+#: settings.cpp:154
+msgid "Support for the HTML 5 local storage feature."
+msgstr "Supporto per lo storage locale di HTML 5"
+
+#: tabbar.cpp:108
+msgid "Clone Tab"
+msgstr "Clona tab"
+
+#: tabbar.cpp:111
+msgid "Close &Other Tabs"
+msgstr "Chiudi le altre tab"
+
+#: tabbar.cpp:113
+msgid "Reload Tab"
+msgstr "Ricarica tab"
+
+#: tabbar.cpp:119
+msgid "Reload All Tabs"
+msgstr "Ricarica tutte le tabs"
+
+#: webview.cpp:245
+msgid "Error loading page: "
+msgstr "Errore nel caricamento della pagina"
+
+#: webview.cpp:309
+msgid "Open Link in New &Tab"
+msgstr "Apri link in una nuova tab"
+
+#: webview.cpp:315
+msgid "Cu&t"
+msgstr "Taglia"
+
+#: webview.cpp:320
+msgid "&Copy"
+msgstr "Copia"
+
+#: webview.cpp:325
+msgid "&Paste"
+msgstr "Incolla"
+
+#: webview.cpp:330
+msgid "&Save Image As..."
+msgstr "Salva Immagine come.."
+
+#: webview.cpp:335
+msgid "&Copy This Image"
+msgstr "Copia immagine"
+
+#: webview.cpp:340
+msgid "&Save Link As..."
+msgstr "Salva link.."
+
+#: webview.cpp:345
+msgid "&Copy Link Location"
+msgstr "Copia link"
+
+#: webview.cpp:350
+msgid "&Inspect Element"
+msgstr "&Ispeziona elemento"
+
+#: webview.cpp:364
+msgid "Bookmark This Page"
+msgstr "Inserisci pagina nei bookmarks"
+
+#: webview.cpp:417
+msgid "&Bookmark This Link"
+msgstr "Inserisci link nei Bookmarks"
+
+#. i18n: file: cookies.ui:14
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesDialog)
+#. i18n: file: settings_privacy.ui:73
+#. i18n: ectx: property (title), widget (QGroupBox, cookiesGroupBox)
+#: rc.cpp:3 rc.cpp:180
+msgid "Cookies"
+msgstr ""
+
+#. i18n: file: cookies.ui:41
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: cookiesexceptions.ui:114
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: history.ui:40
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#: rc.cpp:6 rc.cpp:33 rc.cpp:42
+msgid "&Remove"
+msgstr "Rimuovi"
+
+#. i18n: file: cookies.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:9
+msgid "Remove &All Cookies"
+msgstr "Rimuovi tutti i cookies"
+
+#. i18n: file: cookiesexceptions.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesExceptionsDialog)
+#: rc.cpp:12
+msgid "Cookie Exceptions"
+msgstr "Eccezioni"
+
+#. i18n: file: cookiesexceptions.ui:19
+#. i18n: ectx: property (title), widget (QGroupBox, newExceptionGroupBox)
+#: rc.cpp:15
+msgid "New Exception"
+msgstr "Nuova eccezione"
+
+#. i18n: file: cookiesexceptions.ui:27
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:18
+msgid "Domain:"
+msgstr "Dominio:"
+
+#. i18n: file: cookiesexceptions.ui:89
+#. i18n: ectx: property (title), widget (QGroupBox, ExceptionsGroupBox)
+#: rc.cpp:30
+msgid "Exceptions"
+msgstr "Eccezioni"
+
+#. i18n: file: cookiesexceptions.ui:121
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#. i18n: file: history.ui:47
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:36 rc.cpp:45
+msgid "Remove &All"
+msgstr "Rimuovi tutti"
+
+#. i18n: file: password.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, passwordWidget)
+#. i18n: file: proxy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxyWidget)
+#. i18n: file: settings_webkit.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, webkit)
+#: rc.cpp:48 rc.cpp:63 rc.cpp:243
+msgid "Form"
+msgstr ""
+
+#. i18n: file: password.ui:22
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:51
+msgid "DUMMY ICON"
+msgstr ""
+
+#. i18n: file: password.ui:35
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:54
+msgid "INTRO TEXT DUMMY"
+msgstr ""
+
+#. i18n: file: password.ui:44
+#. i18n: ectx: property (text), widget (QLabel, label)
+#. i18n: file: proxy.ui:37
+#. i18n: ectx: property (text), widget (QLabel, usernameLabel)
+#. i18n: file: settings_proxy.ui:102
+#. i18n: ectx: property (text), widget (QLabel, label_12)
+#: rc.cpp:57 rc.cpp:72 rc.cpp:237
+msgid "Username:"
+msgstr ""
+
+#. i18n: file: password.ui:54
+#. i18n: ectx: property (text), widget (QLabel, lblPassword)
+#. i18n: file: proxy.ui:47
+#. i18n: ectx: property (text), widget (QLabel, passwordLabel)
+#. i18n: file: settings_proxy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label_13)
+#: rc.cpp:60 rc.cpp:75 rc.cpp:240
+msgid "Password:"
+msgstr ""
+
+#. i18n: file: proxy.ui:20
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:66
+msgid "ICON"
+msgstr ""
+
+#. i18n: file: proxy.ui:27
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:69
+msgid "Connect to proxy"
+msgstr "Connetti al proxy"
+
+#. i18n: file: rekonqui.rc:8
+#. i18n: ectx: Menu (file)
+#: rc.cpp:78
+msgid "&File"
+msgstr "&File"
+
+#. i18n: file: rekonqui.rc:24
+#. i18n: ectx: Menu (edit)
+#: rc.cpp:81
+msgid "&Edit"
+msgstr "&Modifica"
+
+#. i18n: file: rekonqui.rc:38
+#. i18n: ectx: Menu (view)
+#: rc.cpp:84
+msgid "&View"
+msgstr "&Vedi"
+
+#. i18n: file: rekonqui.rc:54
+#. i18n: ectx: Menu (go)
+#: rc.cpp:87
+msgid "Hi&story"
+msgstr "&Cronologia"
+
+#. i18n: file: rekonqui.rc:62
+#. i18n: ectx: Menu (tools)
+#: rc.cpp:93
+msgid "&Tools"
+msgstr "&Strumenti"
+
+#. i18n: file: rekonqui.rc:68
+#. i18n: ectx: Menu (settings)
+#: rc.cpp:96
+msgid "&Settings"
+msgstr "&Impostazioni"
+
+#. i18n: file: rekonqui.rc:73
+#. i18n: ectx: Menu (side_panels)
+#: rc.cpp:99
+msgid "Side &Panels"
+msgstr "&Pannelli laterali"
+
+#. i18n: file: rekonqui.rc:88
+#. i18n: ectx: ToolBar (mainToolBar)
+#: rc.cpp:102
+msgid "Main Toolbar"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:100
+#. i18n: ectx: ToolBar (bookmarksToolBar)
+#: rc.cpp:105
+msgid "Bookmark Toolbar"
+msgstr ""
+
+#. i18n: file: settings_fonts.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, fonts)
+#: rc.cpp:108
+msgid "Appearance"
+msgstr "Aspetto"
+
+#. i18n: file: settings_fonts.ui:28
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:114
+msgid "Standard Font"
+msgstr "Carattere standard"
+
+#. i18n: file: settings_fonts.ui:35
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:117
+msgid "Fixed Font"
+msgstr "Carattere fisso"
+
+#. i18n: file: settings_fonts.ui:53
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: rc.cpp:120
+msgid "Dimension"
+msgstr "Dimensione"
+
+#. i18n: file: settings_fonts.ui:61
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:123
+msgid "Font Size"
+msgstr "Dimensione carattere"
+
+#. i18n: file: settings_general.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:129
+msgid "Places"
+msgstr "Come si traduce \"places\"?"
+
+#. i18n: file: settings_general.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:132
+msgid "Home Page:"
+msgstr ""
+
+#. i18n: file: settings_general.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, setHomeToCurrentPageButton)
+#: rc.cpp:135
+msgid "Set to current page"
+msgstr "Imposta alla pagina corrente"
+
+#. i18n: file: settings_general.ui:73
+#. i18n: ectx: property (text), widget (QLabel, label_7)
+#: rc.cpp:138
+msgid "Save downloads to:"
+msgstr "Salva download:"
+
+#. i18n: file: settings_general.ui:83
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_downloadToDefaultDir)
+#: rc.cpp:141
+msgid "ask where saving downloads"
+msgstr "Chiedi dove salvare i downloads"
+
+#. i18n: file: settings_general.ui:93
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_3)
+#: rc.cpp:144
+msgid "Tabbed Browsing"
+msgstr "Navigazione Anonima"
+
+#. i18n: file: settings_general.ui:99
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_alwaysShowTabBar)
+#: rc.cpp:147
+msgid "Always show tab bar"
+msgstr "Mostra sempre la tab bar"
+
+#. i18n: file: settings_general.ui:106
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_openTabsBack)
+#: rc.cpp:150
+msgid "Open tabs in the background"
+msgstr "Apri le nuove tab in background"
+
+#. i18n: file: settings_privacy.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_4)
+#: rc.cpp:159
+msgid "Remove history items:"
+msgstr "Rimuovi la cronologia:"
+
+#. i18n: file: settings_privacy.ui:37
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:162
+msgid "After one day"
+msgstr "Dopo 1 giorno"
+
+#. i18n: file: settings_privacy.ui:42
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:165
+msgid "After one week"
+msgstr "Dopo 1 settimana"
+
+#. i18n: file: settings_privacy.ui:47
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:168
+msgid "After two weeks"
+msgstr "Dopo 2 settimane"
+
+#. i18n: file: settings_privacy.ui:52
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:171
+msgid "After one month"
+msgstr "Dopo 1 mese"
+
+#. i18n: file: settings_privacy.ui:57
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:174
+msgid "After one year"
+msgstr "Dopo 1 anno"
+
+#. i18n: file: settings_privacy.ui:62
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:177
+msgid "Manually"
+msgstr "Manualmente"
+
+#. i18n: file: settings_privacy.ui:79
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:183
+msgid "Accept Cookies:"
+msgstr "Accetta Cookies:"
+
+#. i18n: file: settings_privacy.ui:90
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:186
+msgid "Always"
+msgstr "Sempre"
+
+#. i18n: file: settings_privacy.ui:95
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:189
+msgid "Never"
+msgstr "Mai"
+
+#. i18n: file: settings_privacy.ui:100
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:192
+msgid "Only from sites you visit"
+msgstr "Solo dai siti che visiti"
+
+#. i18n: file: settings_privacy.ui:108
+#. i18n: ectx: property (text), widget (QPushButton, exceptionsButton)
+#: rc.cpp:195
+msgid "Exceptions..."
+msgstr "Eccezioni.."
+
+#. i18n: file: settings_privacy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:198
+msgid "Keep until:"
+msgstr "Mantieni finché"
+
+#. i18n: file: settings_privacy.ui:126
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:201
+msgid "They expire"
+msgstr "non scadono"
+
+#. i18n: file: settings_privacy.ui:131
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:204
+msgid "I exit the application"
+msgstr "esci dall'applicazione"
+
+#. i18n: file: settings_privacy.ui:136
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:207
+msgid "At most 90 days"
+msgstr "Al massimo 90 giorni"
+
+#. i18n: file: settings_privacy.ui:144
+#. i18n: ectx: property (text), widget (QPushButton, cookiesButton)
+#: rc.cpp:210
+msgid "Cookies..."
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:19
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_isProxyEnabled)
+#: rc.cpp:216
+msgid "Enable proxy"
+msgstr "Abilita proxy"
+
+#. i18n: file: settings_proxy.ui:26
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:219
+msgid "Proxy Settings"
+msgstr "Impostazioni Proxy:"
+
+#. i18n: file: settings_proxy.ui:32
+#. i18n: ectx: property (text), widget (QLabel, label_9)
+#: rc.cpp:222
+msgid "Type:"
+msgstr "Tipo:"
+
+#. i18n: file: settings_proxy.ui:43
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:225
+msgid "SOCKS 5"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:48
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:228
+msgid "HTTP"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:56
+#. i18n: ectx: property (text), widget (QLabel, label_10)
+#: rc.cpp:231
+msgid "Host:"
+msgstr "Host:"
+
+#. i18n: file: settings_proxy.ui:69
+#. i18n: ectx: property (text), widget (QLabel, label_11)
+#: rc.cpp:234
+msgid "Port:"
+msgstr "Porta:"
+
+#. i18n: file: settings_webkit.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:246
+msgid "WebKit Settings"
+msgstr "Impostazioni WebKit"
+
+#. i18n: file: settings_webkit.ui:26
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_autoLoadImages)
+#: rc.cpp:249
+msgid "Auto Load Images"
+msgstr "Carica automaticamente immagini"
+
+#. i18n: file: settings_webkit.ui:40
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_linksIncludedInFocusChain)
+#: rc.cpp:252
+msgid "Links included in focus chain"
+msgstr "link inclusi nella sequenza di focus"
+
+#. i18n: file: settings_webkit.ui:47
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptEnabled)
+#: rc.cpp:255
+msgid "Javascript support"
+msgstr "Supporto a Javascript"
+
+#. i18n: file: settings_webkit.ui:54
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_zoomTextOnly)
+#: rc.cpp:258
+msgid "Zoom Text Only"
+msgstr "Zoom solo testo"
+
+#. i18n: file: settings_webkit.ui:61
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javaEnabled)
+#: rc.cpp:261
+msgid "Java support"
+msgstr "supporto a Java"
+
+#. i18n: file: settings_webkit.ui:68
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_printElementBackgrounds)
+#: rc.cpp:264
+msgid "Print element Backgrounds"
+msgstr "Stampa gli elementi di sfondo"
+
+#. i18n: file: settings_webkit.ui:75
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_pluginsEnabled)
+#: rc.cpp:267
+msgid "Plugins"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:82
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineStorageDatabaseEnabled)
+#: rc.cpp:270
+msgid "Offline storage Database"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:89
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanOpenWindows)
+#: rc.cpp:273
+msgid "Javascript can open windows"
+msgstr "javascript può aprire finestre"
+
+#. i18n: file: settings_webkit.ui:96
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineWebApplicationCacheEnabled)
+#: rc.cpp:276
+msgid "Offline Web Application Cache "
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:103
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanAccessClipboard)
+#: rc.cpp:279
+msgid "Javascript can access clipboard"
+msgstr "javascript può accedere alla clipboard"
+
+#. i18n: file: settings_webkit.ui:110
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_localStorageDatabaseEnabled)
+#: rc.cpp:282
+msgid "Local storage database"
+msgstr ""
+
+#~ msgid "Show side panel"
+#~ msgstr "Mostra il pannello laterale"
+
+#~ msgid "Print Document"
+#~ msgstr "Stampa Documento"
+
+#~ msgid "reload"
+#~ msgstr "ricarica"
+
+#~ msgid "Clear Location Bar"
+#~ msgstr "Cancella la Barra degli Indirizzi"
+
+#~ msgid ""
+#~ "<html>Clear Location bar<br /><br />Clears the contents of the location "
+#~ "bar.</html>"
+#~ msgstr ""
+#~ "<html>Cancella la barra degli indirizzi<br /><br /> Cancella il contenuto "
+#~ "della barra degli indirizzi"
diff --git a/po/rekonq_ru.po b/po/rekonq_ru.po
new file mode 100644
index 00000000..91dfb2ec
--- /dev/null
+++ b/po/rekonq_ru.po
@@ -0,0 +1,1134 @@
+# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
+# This file is distributed under the same license as the rekonq package.
+# FIRST AUTHOR Domrachev Alexandr <alexnadr.domrachev@gmail.com>, 2009.
+# Domrachev Alexandr <alexandr.domrachev@gmail.com>, 2009.
+msgid ""
+msgstr ""
+"Project-Id-Version: \n"
+"Report-Msgid-Bugs-To: http://sourceforge.net/tracker/?"
+"group_id=252277&atid=1126949\n"
+"POT-Creation-Date: 2009-05-02 02:35+0200\n"
+"PO-Revision-Date: 2009-04-18 22:21+0400\n"
+"Last-Translator: Domrachev Alexandr <alexandr.domrachev@gmail.com>\n"
+"Language-Team: Russian <kde-russian@lists.kde.ru>\n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Language: ru_RU\n"
+"X-Generator: Lokalize 0.3\n"
+"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%"
+"10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
+
+#. i18n: file: rekonqui.rc:58
+#. i18n: ectx: Menu (go)
+#: bookmarks.cpp:265 rc.cpp:90
+msgid "&Bookmarks"
+msgstr "&Закладки"
+
+#: bookmarks.cpp:274
+msgid "Bookmarks Bar"
+msgstr "Панель закладок"
+
+#: cookiejar.cpp:457 cookiejar.cpp:636
+msgid "Website"
+msgstr "Сайт"
+
+#: cookiejar.cpp:459
+msgid "Name"
+msgstr "Имя"
+
+#: cookiejar.cpp:461
+msgid "Path"
+msgstr "Путь"
+
+#: cookiejar.cpp:463
+msgid "Secure"
+msgstr ""
+
+#: cookiejar.cpp:465
+msgid "Expires"
+msgstr "Истекает"
+
+#: cookiejar.cpp:467
+msgid "Contents"
+msgstr "Содержимое"
+
+#: cookiejar.cpp:638
+msgid "Status"
+msgstr "Статус"
+
+#. i18n: file: cookiesexceptions.ui:77
+#. i18n: ectx: property (text), widget (QPushButton, allowButton)
+#: cookiejar.cpp:663 rc.cpp:27
+msgid "Allow"
+msgstr "Разрешить"
+
+#. i18n: file: cookiesexceptions.ui:57
+#. i18n: ectx: property (text), widget (QPushButton, blockButton)
+#: cookiejar.cpp:674 rc.cpp:21
+msgid "Block"
+msgstr "Блокировать"
+
+#. i18n: file: cookiesexceptions.ui:67
+#. i18n: ectx: property (text), widget (QPushButton, allowForSessionButton)
+#: cookiejar.cpp:685 rc.cpp:24
+msgid "Allow For Session"
+msgstr "Разрешить до конца сессии"
+
+#: download.cpp:73
+msgid ""
+"Download '%1'?\n"
+"Type: %2"
+msgstr ""
+"Загрузить '%1'?\n"
+"Тип: %2"
+
+#: download.cpp:74
+msgid "Download '%1'..."
+msgstr "Загрузка '%1'..."
+
+#: findbar.cpp:39
+msgid "&Match case"
+msgstr "С учётом &регистра"
+
+#: findbar.cpp:55
+msgid "Find: "
+msgstr "Поиск:"
+
+#: findbar.cpp:65
+msgid "&Next"
+msgstr "&Вперед"
+
+#: findbar.cpp:66
+msgid "&Previous"
+msgstr "&Назад"
+
+#: history.cpp:445
+msgid "Title"
+msgstr ""
+
+#: history.cpp:446
+msgid "Address"
+msgstr ""
+
+#: history.cpp:703
+msgid "Show All History"
+msgstr "Открыть журнал"
+
+#: history.cpp:707
+msgid "Clear History"
+msgstr "Очистить журнал"
+
+#: history.cpp:788
+msgid "Open"
+msgstr "Открыть"
+
+#: history.cpp:790
+msgid "Copy"
+msgstr "Копировать"
+
+#: history.cpp:792
+msgid "Delete"
+msgstr "Удалить"
+
+#: history.cpp:1175
+msgid "Earlier Today"
+msgstr "Сегодня ранее"
+
+#: history.cpp:1180
+msgid "1 item"
+msgid_plural "%1 items"
+msgstr[0] ""
+msgstr[1] ""
+msgstr[2] ""
+
+#: main.cpp:29
+msgid "KDE Browser Webkit Based"
+msgstr ""
+
+#: main.cpp:39
+msgid "rekonq"
+msgstr ""
+
+#: main.cpp:43
+msgid "(C) 2008-2009 Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:50
+msgid "Andrea Diamantini"
+msgstr ""
+
+#: main.cpp:51
+msgid "Project Lead, Developer, Italian translations"
+msgstr ""
+
+#: main.cpp:55
+msgid "Domrachev Alexandr"
+msgstr "Домрачев Александр"
+
+#: main.cpp:56
+msgid "Developer, Russian translations"
+msgstr ""
+
+#: main.cpp:60
+msgid "Pawel Prazak"
+msgstr ""
+
+#: main.cpp:61
+msgid "Developer"
+msgstr ""
+
+#: main.cpp:65
+msgid "Panagiotis Papadopoulos"
+msgstr ""
+
+#: main.cpp:66
+msgid "German translations"
+msgstr ""
+
+#: main.cpp:82
+msgid "Location to open"
+msgstr ""
+
+#: mainview.cpp:98
+msgid "Recently Closed Tabs"
+msgstr "Недавно закрытые вкладки"
+
+#: mainview.cpp:339 mainview.cpp:583
+msgid "(Untitled)"
+msgstr "(Без заголовка)"
+
+#: mainview.cpp:455
+msgid ""
+"You have modified this page and when closing it you would lose the "
+"modification.\n"
+"Do you really want to close this page?\n"
+msgstr ""
+"Вы изменили данную страницу, при закрытии Вы потеряете все изменения.\n"
+"Вы действительно хотите закрыть эту страницу?\n"
+
+#: mainview.cpp:457
+msgid "Do you really want to close this page?"
+msgstr "Вы действительно хотите закрыть эту страницу?"
+
+#: mainview.cpp:514
+msgid "Loading..."
+msgstr "Загрузка..."
+
+#: mainview.cpp:529
+msgid "Loading %1% (%2 %3)..."
+msgstr "Загрузка %1% (%2 %3)..."
+
+#: mainview.cpp:556
+msgid "Done"
+msgstr ""
+
+#: mainview.cpp:558
+msgid "Failed to load"
+msgstr "Ошибка загрузки"
+
+#: mainwindow.cpp:177
+msgid "Location Bar"
+msgstr "Отрыть местоположение"
+
+#: mainwindow.cpp:183
+msgid "Search Bar"
+msgstr "Поиск..."
+
+#: mainwindow.cpp:215 mainwindow.cpp:230 mainwindow.cpp:809
+msgid "Reload"
+msgstr "Обновить"
+
+#: mainwindow.cpp:224
+#, fuzzy
+msgid "&Stop"
+msgstr "&Стоп"
+
+#: mainwindow.cpp:235
+msgid "Open Location"
+msgstr "Отрыть местоположение"
+
+#: mainwindow.cpp:240
+msgid "&Enlarge Font"
+msgstr "У&величить шрифт"
+
+#: mainwindow.cpp:245
+msgid "&Normal Font"
+msgstr "&Нормальный шрифт"
+
+#: mainwindow.cpp:250
+msgid "&Shrink Font"
+msgstr "У&меньшить шрифт"
+
+#: mainwindow.cpp:255
+msgid "Page S&ource"
+msgstr "Исходный &код"
+
+#: mainwindow.cpp:260
+#, fuzzy
+msgid "Web &Inspector"
+msgstr "Включить Web &Inspector"
+
+#: mainwindow.cpp:265
+#, fuzzy
+msgid "Private &Browsing"
+msgstr "Режим &конфиденциальности..."
+
+#: mainwindow.cpp:271
+msgid "Back"
+msgstr "Назад"
+
+#: mainwindow.cpp:279
+msgid "Forward"
+msgstr "Вперед"
+
+#: mainwindow.cpp:284
+msgid "New &Tab"
+msgstr "Новая &вкладка"
+
+#: mainwindow.cpp:292 tabbar.cpp:110
+msgid "&Close Tab"
+msgstr "&Закрыть вкладку"
+
+#: mainwindow.cpp:297
+msgid "Show Next Tab"
+msgstr "Открыть следующую вкладку"
+
+#: mainwindow.cpp:302
+msgid "Show Previous Tab"
+msgstr "Открыть предыдущую вкладку"
+
+#. i18n: file: history.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, HistoryDialog)
+#. i18n: file: settings_privacy.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: mainwindow.cpp:312 mainwindow.cpp:320 rc.cpp:39 rc.cpp:156
+msgid "History"
+msgstr "Журнал"
+
+#: mainwindow.cpp:336
+msgid "&History"
+msgstr "&Журнал"
+
+#: mainwindow.cpp:523
+#, fuzzy
+msgid "Web Resources (*.html *.htm *.svg *.png *.gif *.svgz); All files (*.*)"
+msgstr "Веб ресурсы (*.html *.htm *.svg *.png *.gif *.svgz);;All files (*.*)"
+
+#: mainwindow.cpp:525
+msgid "Open Web Resource"
+msgstr "Открыть..."
+
+#: mainwindow.cpp:571
+msgid "Are you sure you want to turn on private browsing?"
+msgstr "Вы действительно хотите включить режим конфиденциальности?"
+
+#: mainwindow.cpp:572
+#, fuzzy
+msgid ""
+"</b><br><br>When private browsing in turned on, webpages are not added to "
+"the history, new cookies are not stored, current cookies cannot be accessed, "
+"site icons will not be stored, session will not be saved, and searches are "
+"not addded to the pop-up menu in the Google search box. Until you close the "
+"window, you can still click the Back and Forward buttons to return to the "
+"webpages you have opened."
+msgstr ""
+"</b><br><br>При включенном режиме конфиденциальности, страницы не "
+"добавляются в журнал, по завершении загрузки они удаляются из списка "
+"загрузок, новые cookie не сохраняются, к уже имеющимся доступ закрыт, "
+"история поиска не сохраняется. Пока Вы не закроете окно, Вы можете "
+"использовать кнопки \"Вперед\" и \"Назад\" для перемещения по уже посещенным "
+"сайтам."
+
+#: mainwindow.cpp:632 mainwindow.cpp:654
+msgid " not found."
+msgstr "не найдено."
+
+#: mainwindow.cpp:766
+msgid ""
+"The web inspector will only work correctly for pages that were loaded after "
+"enabling.\n"
+"Do you want to reload all pages?"
+msgstr ""
+"Web Inspector будет работать нормально только для страниц загруженных после "
+"его включения.\n"
+"Вы хотите обновить все вкладки?"
+
+#: mainwindow.cpp:768
+msgid "Web Inspector"
+msgstr ""
+
+#: mainwindow.cpp:800
+msgid "Stop loading the current page"
+msgstr "Остановить загрузку страницы"
+
+#: mainwindow.cpp:801
+msgid "Stop"
+msgstr ""
+
+#: mainwindow.cpp:808
+msgid "Reload the current page"
+msgstr "Обновить страницу"
+
+#: mainwindow.cpp:892
+#, fuzzy
+msgid ""
+"Are you sure you want to close the window?\n"
+"You have 1 tap open"
+msgid_plural ""
+"Are you sure you want to close the window?\n"
+"You have %1 tabs open"
+msgstr[0] ""
+"Вы действительно хотите закрыть окно?\n"
+"У Вас окрыто %1 вкладк(а,и,ок)"
+msgstr[1] ""
+"Вы действительно хотите закрыть окно?\n"
+"У Вас окрыто %1 вкладк(а,и,ок)"
+msgstr[2] ""
+"Вы действительно хотите закрыть окно?\n"
+"У Вас окрыто %1 вкладк(а,и,ок)"
+
+#: mainwindow.cpp:893
+msgid "Are you sure you want to close the window?"
+msgstr " Вы уверены, что хотите закрыть окно?"
+
+#: mainwindow.cpp:895
+#, fuzzy
+msgid "C&lose Current Tab"
+msgstr "&Закрыть вкладку"
+
+#: networkaccessmanager.cpp:112
+msgid "<qt>Enter username and password for "
+msgstr "<qt>Введите имя пользователя и пароль для "
+
+#: networkaccessmanager.cpp:113
+msgid " at "
+msgstr ""
+
+#: networkaccessmanager.cpp:140
+msgid "<qt>Connect to proxy "
+msgstr ""
+
+#: networkaccessmanager.cpp:140
+msgid " using:</qt>"
+msgstr ""
+
+#: networkaccessmanager.cpp:160
+msgid ""
+"SSL Errors:\n"
+"\n"
+msgstr ""
+
+#: panelhistory.cpp:50
+msgid "Search: "
+msgstr "Поиск: "
+
+#: searchbar.cpp:55
+#, fuzzy
+msgid "Search.."
+msgstr "Поиск..."
+
+#. i18n: file: settings_general.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, general)
+#: settings.cpp:81 rc.cpp:126
+msgid "General"
+msgstr "Основное"
+
+#. i18n: file: settings_fonts.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: settings.cpp:87 rc.cpp:111
+msgid "Fonts"
+msgstr "Шрифты"
+
+#. i18n: file: settings_privacy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, privacy)
+#: settings.cpp:93 rc.cpp:153
+msgid "Privacy"
+msgstr "Приватность"
+
+#. i18n: file: settings_proxy.ui:13
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxy)
+#: settings.cpp:99 rc.cpp:213
+msgid "Proxy"
+msgstr "Прокси"
+
+#: settings.cpp:105
+msgid "Webkit"
+msgstr ""
+
+#: settings.cpp:121
+#, fuzzy
+msgid "rekonfig.."
+msgstr "Параметры..."
+
+#: settings.cpp:143
+msgid "Specifies whether images are automatically loaded in web pages"
+msgstr ""
+
+#: settings.cpp:144
+msgid "Enables the running of JavaScript programs."
+msgstr ""
+
+#: settings.cpp:145
+msgid "Enables Java applets."
+msgstr ""
+
+#: settings.cpp:146
+msgid "Enables plugins in web pages."
+msgstr "Включает использование плагинов на странице"
+
+#: settings.cpp:147
+msgid "Allows JavaScript programs to opening new windows."
+msgstr ""
+
+#: settings.cpp:148
+msgid "Allows JavaScript programs to reading/writing to the clipboard."
+msgstr ""
+
+#: settings.cpp:149
+msgid "Includes hyperlinks in the keyboard focus chain."
+msgstr ""
+
+#: settings.cpp:150
+msgid "Applies the zoom factor on a frame to only the text or all content."
+msgstr ""
+
+#: settings.cpp:151
+msgid "Draws also background color and images when the page is printed."
+msgstr ""
+
+#: settings.cpp:152
+msgid "Support for the HTML 5 offline storage feature."
+msgstr ""
+
+#: settings.cpp:153
+msgid "Support for the HTML 5 web application cache feature."
+msgstr ""
+
+#: settings.cpp:154
+msgid "Support for the HTML 5 local storage feature."
+msgstr ""
+
+#: tabbar.cpp:108
+msgid "Clone Tab"
+msgstr "Закрыть вкладку"
+
+#: tabbar.cpp:111
+msgid "Close &Other Tabs"
+msgstr "Закрыть все, &кроме активной"
+
+#: tabbar.cpp:113
+msgid "Reload Tab"
+msgstr "Обновить вкладку"
+
+#: tabbar.cpp:119
+msgid "Reload All Tabs"
+msgstr "Обновить все вкладки"
+
+#: webview.cpp:245
+msgid "Error loading page: "
+msgstr "Ошибка загрузки страницы: "
+
+#: webview.cpp:309
+msgid "Open Link in New &Tab"
+msgstr "Открыть ссылку в &новой вкладке"
+
+#: webview.cpp:315
+msgid "Cu&t"
+msgstr ""
+
+#: webview.cpp:320
+msgid "&Copy"
+msgstr ""
+
+#: webview.cpp:325
+msgid "&Paste"
+msgstr ""
+
+#: webview.cpp:330
+msgid "&Save Image As..."
+msgstr "&Сохранить изображение..."
+
+#: webview.cpp:335
+msgid "&Copy This Image"
+msgstr "&Копировать изображение в буфер обмена"
+
+#: webview.cpp:340
+msgid "&Save Link As..."
+msgstr "Сохранить по ссылке как..."
+
+#: webview.cpp:345
+msgid "&Copy Link Location"
+msgstr "&Отрыть местоположение"
+
+#: webview.cpp:350
+msgid "&Inspect Element"
+msgstr ""
+
+#: webview.cpp:364
+msgid "Bookmark This Page"
+msgstr "Создать закладку"
+
+#: webview.cpp:417
+msgid "&Bookmark This Link"
+msgstr "Создать &закладку ссылки"
+
+#. i18n: file: cookies.ui:14
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesDialog)
+#. i18n: file: settings_privacy.ui:73
+#. i18n: ectx: property (title), widget (QGroupBox, cookiesGroupBox)
+#: rc.cpp:3 rc.cpp:180
+msgid "Cookies"
+msgstr ""
+
+#. i18n: file: cookies.ui:41
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: cookiesexceptions.ui:114
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#. i18n: file: history.ui:40
+#. i18n: ectx: property (text), widget (QPushButton, removeButton)
+#: rc.cpp:6 rc.cpp:33 rc.cpp:42
+msgid "&Remove"
+msgstr "&Удалить"
+
+#. i18n: file: cookies.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:9
+msgid "Remove &All Cookies"
+msgstr "Удалить &все cookie"
+
+#. i18n: file: cookiesexceptions.ui:13
+#. i18n: ectx: property (windowTitle), widget (QDialog, CookiesExceptionsDialog)
+#: rc.cpp:12
+msgid "Cookie Exceptions"
+msgstr "Исключения для cookies"
+
+#. i18n: file: cookiesexceptions.ui:19
+#. i18n: ectx: property (title), widget (QGroupBox, newExceptionGroupBox)
+#: rc.cpp:15
+msgid "New Exception"
+msgstr "Новое исключение"
+
+#. i18n: file: cookiesexceptions.ui:27
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:18
+msgid "Domain:"
+msgstr ""
+
+#. i18n: file: cookiesexceptions.ui:89
+#. i18n: ectx: property (title), widget (QGroupBox, ExceptionsGroupBox)
+#: rc.cpp:30
+msgid "Exceptions"
+msgstr "Исключения"
+
+#. i18n: file: cookiesexceptions.ui:121
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#. i18n: file: history.ui:47
+#. i18n: ectx: property (text), widget (QPushButton, removeAllButton)
+#: rc.cpp:36 rc.cpp:45
+msgid "Remove &All"
+msgstr "Удалить &всё"
+
+#. i18n: file: password.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, passwordWidget)
+#. i18n: file: proxy.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, proxyWidget)
+#. i18n: file: settings_webkit.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, webkit)
+#: rc.cpp:48 rc.cpp:63 rc.cpp:243
+msgid "Form"
+msgstr ""
+
+#. i18n: file: password.ui:22
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:51
+msgid "DUMMY ICON"
+msgstr ""
+
+#. i18n: file: password.ui:35
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:54
+msgid "INTRO TEXT DUMMY"
+msgstr ""
+
+#. i18n: file: password.ui:44
+#. i18n: ectx: property (text), widget (QLabel, label)
+#. i18n: file: proxy.ui:37
+#. i18n: ectx: property (text), widget (QLabel, usernameLabel)
+#. i18n: file: settings_proxy.ui:102
+#. i18n: ectx: property (text), widget (QLabel, label_12)
+#: rc.cpp:57 rc.cpp:72 rc.cpp:237
+msgid "Username:"
+msgstr "Имя пользователя:"
+
+#. i18n: file: password.ui:54
+#. i18n: ectx: property (text), widget (QLabel, lblPassword)
+#. i18n: file: proxy.ui:47
+#. i18n: ectx: property (text), widget (QLabel, passwordLabel)
+#. i18n: file: settings_proxy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label_13)
+#: rc.cpp:60 rc.cpp:75 rc.cpp:240
+msgid "Password:"
+msgstr "Пароль:"
+
+#. i18n: file: proxy.ui:20
+#. i18n: ectx: property (text), widget (QLabel, iconLabel)
+#: rc.cpp:66
+msgid "ICON"
+msgstr ""
+
+#. i18n: file: proxy.ui:27
+#. i18n: ectx: property (text), widget (QLabel, introLabel)
+#: rc.cpp:69
+msgid "Connect to proxy"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:8
+#. i18n: ectx: Menu (file)
+#: rc.cpp:78
+msgid "&File"
+msgstr "&Файл"
+
+#. i18n: file: rekonqui.rc:24
+#. i18n: ectx: Menu (edit)
+#: rc.cpp:81
+msgid "&Edit"
+msgstr "&Правка"
+
+#. i18n: file: rekonqui.rc:38
+#. i18n: ectx: Menu (view)
+#: rc.cpp:84
+msgid "&View"
+msgstr "&Вид"
+
+#. i18n: file: rekonqui.rc:54
+#. i18n: ectx: Menu (go)
+#: rc.cpp:87
+msgid "Hi&story"
+msgstr "&Журнал"
+
+#. i18n: file: rekonqui.rc:62
+#. i18n: ectx: Menu (tools)
+#: rc.cpp:93
+msgid "&Tools"
+msgstr ""
+
+#. i18n: file: rekonqui.rc:68
+#. i18n: ectx: Menu (settings)
+#: rc.cpp:96
+msgid "&Settings"
+msgstr "&Настройки"
+
+#. i18n: file: rekonqui.rc:73
+#. i18n: ectx: Menu (side_panels)
+#: rc.cpp:99
+msgid "Side &Panels"
+msgstr "Боковые &панели"
+
+#. i18n: file: rekonqui.rc:88
+#. i18n: ectx: ToolBar (mainToolBar)
+#: rc.cpp:102
+msgid "Main Toolbar"
+msgstr "Панель инструментов"
+
+#. i18n: file: rekonqui.rc:100
+#. i18n: ectx: ToolBar (bookmarksToolBar)
+#: rc.cpp:105
+msgid "Bookmark Toolbar"
+msgstr "Панель закладок"
+
+#. i18n: file: settings_fonts.ui:14
+#. i18n: ectx: property (windowTitle), widget (QWidget, fonts)
+#: rc.cpp:108
+msgid "Appearance"
+msgstr "Внешний вид"
+
+#. i18n: file: settings_fonts.ui:28
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:114
+msgid "Standard Font"
+msgstr "Стандартный шрифт"
+
+#. i18n: file: settings_fonts.ui:35
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:117
+msgid "Fixed Font"
+msgstr "Моноширинный шрифт"
+
+#. i18n: file: settings_fonts.ui:53
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_2)
+#: rc.cpp:120
+msgid "Dimension"
+msgstr "Размеры"
+
+#. i18n: file: settings_fonts.ui:61
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:123
+msgid "Font Size"
+msgstr "Размер шрифта:"
+
+#. i18n: file: settings_general.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:129
+msgid "Places"
+msgstr ""
+
+#. i18n: file: settings_general.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_3)
+#: rc.cpp:132
+#, fuzzy
+msgid "Home Page:"
+msgstr "Адрес:"
+
+#. i18n: file: settings_general.ui:48
+#. i18n: ectx: property (text), widget (QPushButton, setHomeToCurrentPageButton)
+#: rc.cpp:135
+msgid "Set to current page"
+msgstr "Использовать текущую страницу"
+
+#. i18n: file: settings_general.ui:73
+#. i18n: ectx: property (text), widget (QLabel, label_7)
+#: rc.cpp:138
+#, fuzzy
+msgid "Save downloads to:"
+msgstr "&Загружать файлы в:"
+
+#. i18n: file: settings_general.ui:83
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_downloadToDefaultDir)
+#: rc.cpp:141
+msgid "ask where saving downloads"
+msgstr ""
+
+#. i18n: file: settings_general.ui:93
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox_3)
+#: rc.cpp:144
+msgid "Tabbed Browsing"
+msgstr "Вкладки"
+
+#. i18n: file: settings_general.ui:99
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_alwaysShowTabBar)
+#: rc.cpp:147
+msgid "Always show tab bar"
+msgstr "Всегда показывать панель вкладок"
+
+#. i18n: file: settings_general.ui:106
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_openTabsBack)
+#: rc.cpp:150
+msgid "Open tabs in the background"
+msgstr ""
+
+#. i18n: file: settings_privacy.ui:26
+#. i18n: ectx: property (text), widget (QLabel, label_4)
+#: rc.cpp:159
+#, fuzzy
+msgid "Remove history items:"
+msgstr "Удалять записи истории:"
+
+#. i18n: file: settings_privacy.ui:37
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:162
+#, fuzzy
+msgid "After one day"
+msgstr "Каждый день"
+
+#. i18n: file: settings_privacy.ui:42
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:165
+#, fuzzy
+msgid "After one week"
+msgstr "Каждую неделю"
+
+#. i18n: file: settings_privacy.ui:47
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:168
+#, fuzzy
+msgid "After two weeks"
+msgstr "Каждые две недели"
+
+#. i18n: file: settings_privacy.ui:52
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:171
+#, fuzzy
+msgid "After one month"
+msgstr "Каждый месяц"
+
+#. i18n: file: settings_privacy.ui:57
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:174
+#, fuzzy
+msgid "After one year"
+msgstr "Каждый год"
+
+#. i18n: file: settings_privacy.ui:62
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_expireHistory)
+#: rc.cpp:177
+msgid "Manually"
+msgstr "Вручную"
+
+#. i18n: file: settings_privacy.ui:79
+#. i18n: ectx: property (text), widget (QLabel, label_2)
+#: rc.cpp:183
+msgid "Accept Cookies:"
+msgstr "Принимать cookie:"
+
+#. i18n: file: settings_privacy.ui:90
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:186
+msgid "Always"
+msgstr "Всегда"
+
+#. i18n: file: settings_privacy.ui:95
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:189
+msgid "Never"
+msgstr "Никогда"
+
+#. i18n: file: settings_privacy.ui:100
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_acceptCookies)
+#: rc.cpp:192
+msgid "Only from sites you visit"
+msgstr "Только от посещённых сайтов"
+
+#. i18n: file: settings_privacy.ui:108
+#. i18n: ectx: property (text), widget (QPushButton, exceptionsButton)
+#: rc.cpp:195
+msgid "Exceptions..."
+msgstr "Исключения..."
+
+#. i18n: file: settings_privacy.ui:115
+#. i18n: ectx: property (text), widget (QLabel, label)
+#: rc.cpp:198
+msgid "Keep until:"
+msgstr "Хранить до:"
+
+#. i18n: file: settings_privacy.ui:126
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:201
+msgid "They expire"
+msgstr "Их истечения"
+
+#. i18n: file: settings_privacy.ui:131
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:204
+#, fuzzy
+msgid "I exit the application"
+msgstr "Выхода из программы"
+
+#. i18n: file: settings_privacy.ui:136
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_keepCookiesUntil)
+#: rc.cpp:207
+msgid "At most 90 days"
+msgstr "До 90 дней"
+
+#. i18n: file: settings_privacy.ui:144
+#. i18n: ectx: property (text), widget (QPushButton, cookiesButton)
+#: rc.cpp:210
+msgid "Cookies..."
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:19
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_isProxyEnabled)
+#: rc.cpp:216
+msgid "Enable proxy"
+msgstr "Использовать proxy"
+
+#. i18n: file: settings_proxy.ui:26
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:219
+msgid "Proxy Settings"
+msgstr "Настройки proxy"
+
+#. i18n: file: settings_proxy.ui:32
+#. i18n: ectx: property (text), widget (QLabel, label_9)
+#: rc.cpp:222
+msgid "Type:"
+msgstr "Тип:"
+
+#. i18n: file: settings_proxy.ui:43
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:225
+msgid "SOCKS 5"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:48
+#. i18n: ectx: property (text), item, widget (QComboBox, kcfg_proxyType)
+#: rc.cpp:228
+msgid "HTTP"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:56
+#. i18n: ectx: property (text), widget (QLabel, label_10)
+#: rc.cpp:231
+msgid "Host:"
+msgstr ""
+
+#. i18n: file: settings_proxy.ui:69
+#. i18n: ectx: property (text), widget (QLabel, label_11)
+#: rc.cpp:234
+msgid "Port:"
+msgstr "Порт:"
+
+#. i18n: file: settings_webkit.ui:20
+#. i18n: ectx: property (title), widget (QGroupBox, groupBox)
+#: rc.cpp:246
+msgid "WebKit Settings"
+msgstr "Настройки WebKit"
+
+#. i18n: file: settings_webkit.ui:26
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_autoLoadImages)
+#: rc.cpp:249
+msgid "Auto Load Images"
+msgstr "Автоматически загружать картинки"
+
+#. i18n: file: settings_webkit.ui:40
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_linksIncludedInFocusChain)
+#: rc.cpp:252
+msgid "Links included in focus chain"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:47
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptEnabled)
+#: rc.cpp:255
+msgid "Javascript support"
+msgstr "Включить Javascript"
+
+#. i18n: file: settings_webkit.ui:54
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_zoomTextOnly)
+#: rc.cpp:258
+msgid "Zoom Text Only"
+msgstr "Увеличивать только текст"
+
+#. i18n: file: settings_webkit.ui:61
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javaEnabled)
+#: rc.cpp:261
+msgid "Java support"
+msgstr "Включить Java"
+
+#. i18n: file: settings_webkit.ui:68
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_printElementBackgrounds)
+#: rc.cpp:264
+msgid "Print element Backgrounds"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:75
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_pluginsEnabled)
+#: rc.cpp:267
+msgid "Plugins"
+msgstr "Плагины"
+
+#. i18n: file: settings_webkit.ui:82
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineStorageDatabaseEnabled)
+#: rc.cpp:270
+msgid "Offline storage Database"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:89
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanOpenWindows)
+#: rc.cpp:273
+msgid "Javascript can open windows"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:96
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_offlineWebApplicationCacheEnabled)
+#: rc.cpp:276
+msgid "Offline Web Application Cache "
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:103
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_javascriptCanAccessClipboard)
+#: rc.cpp:279
+msgid "Javascript can access clipboard"
+msgstr ""
+
+#. i18n: file: settings_webkit.ui:110
+#. i18n: ectx: property (text), widget (QCheckBox, kcfg_localStorageDatabaseEnabled)
+#: rc.cpp:282
+msgid "Local storage database"
+msgstr ""
+
+#~ msgid "Show side panel"
+#~ msgstr "Боковая панель"
+
+#~ msgid "Print Document"
+#~ msgstr "Печать"
+
+#~ msgid "Location Toolbar"
+#~ msgstr "Адресная строка"
+
+#, fuzzy
+#~ msgid "reload"
+#~ msgstr "Обновить"
+
+#, fuzzy
+#~ msgid "Clear Location Bar"
+#~ msgstr "Отрыть местоположение"
+
+#~ msgid "Finished loading"
+#~ msgstr "Загрузка завершена"
+
+#~ msgid "Bookmarks"
+#~ msgstr "Закладки"
+
+#~ msgid "Interface"
+#~ msgstr "Интерфейс"
+
+#~ msgid "Startup"
+#~ msgstr "Запуск"
+
+#~ msgid "Downloads"
+#~ msgstr "Загрузки"
+
+#~ msgid "&Always show open/save dialog"
+#~ msgstr "&Всегда спрашивать сохранять файл или открывать"
+
+#~ msgid "This option will work only with Qt 4.5 and higher"
+#~ msgstr "Эта опция будет работать с QT4.5 или новее."
+
+#~ msgid "Show close button on tabs"
+#~ msgstr "Показывать кнопку закрытия на вкладках"
+
+#~ msgid "Show corner buttons on tab bar"
+#~ msgstr "Показывать боковые кнопки"
+
+#~ msgid "Confirm when closing window with multiple tabs"
+#~ msgstr "Подтверждать закрытие окна с несколькими вкладками"
+
+#~ msgid "Enable location bar progress indication"
+#~ msgstr "Показывать индикатор загрузки страницы в адресной строке"
+
+#~ msgid "Secure connection indicator:"
+#~ msgstr "Индикатор защищённых соединений:"
+
+#~ msgid "Progress indicator:"
+#~ msgstr "Индикатор прогресса загрузки:"
+
+#~ msgid "Web Content"
+#~ msgstr "Веб-содержимое"
+
+#~ msgid "Ask destination for each download"
+#~ msgstr "Каждый раз спрашивать папку назначения"
+
+#~ msgid "Use one close tab button"
+#~ msgstr "Использовать единую кнопку закрытия вкладок"
+
+#~ msgid "Location bar"
+#~ msgstr "Адресная строка"
+
+#~ msgid "Tab bar"
+#~ msgstr "Вкладки"
+
+#, fuzzy
+#~ msgid "History Dock"
+#~ msgstr "Журнал"
+
+#~ msgid "Copy This Link"
+#~ msgstr "Копировать адрес ссылки"
+
+#~ msgid "Exit rekonq if last tab closed"
+#~ msgstr "Выходить из rekonq при закрытии последней вкладки"
+
+#~ msgid "User Name:"
+#~ msgstr "Логин:"
+
+#~ msgid "private_browsing"
+#~ msgstr "режим конфиденциальности"
diff --git a/rekonq.SlackBuild b/rekonq.SlackBuild
new file mode 100644
index 00000000..2de6ceae
--- /dev/null
+++ b/rekonq.SlackBuild
@@ -0,0 +1,79 @@
+#!/bin/sh
+# Slackware build script for $NAME
+# Heavily based on the Slackware 12.2 SlackBuild
+# Written by Andrea Diamantini - adjam7_AT_gmail_DOT_com
+
+NAME=rekonq
+VERSION=0.0.4
+ARCH=${ARCH:-i486}
+BUILD=1ad
+
+# working dirs
+CWD=$(pwd)
+TMP=$CWD/tmp
+BUILDIR=$TMP/build
+PKG=$TMP/package-$NAME
+
+KDEPREFIX=$(kde4-config --prefix)
+
+JOBS=${JOBS:-2} # Might not be wanted or needed in some cases
+
+if [ "$ARCH" = "i486" ]; then
+ SLKCFLAGS="-O2 -march=i486 -mtune=i686"
+elif [ "$ARCH" = "i686" ]; then
+ SLKCFLAGS="-O3 -march=i686 -pipe -fomit-frame-pointer"
+elif [ "$ARCH" = "athlon64" ]; then
+ SLKCFLAGS="-O2 -march=athlon64 -pipe"
+elif [ "$ARCH" = "athlonxp" ]; then
+ SLKCFLAGS="-O3 -march=athlon-xp -pipe -fomit-frame-pointer"
+elif [ "$ARCH" = "x86_64" ]; then
+ SLKCFLAGS="-O2"
+fi
+
+rm -rf $TMP
+mkdir -p $TMP $PKG $BUILDIR
+
+cd $BUILDIR
+
+# configure option for $NAME
+cmake \
+-DCMAKE_CXX_FLAGS:STRING="$SLKCFLAGS" \
+-DCMAKE_INSTALL_PREFIX=$KDEPREFIX \
+-DCMAKE_BUILD_TYPE=release \
+$CWD
+
+# Compile the application and install it into the $PKG directory
+nice make -j $JOBS || exit 1
+make install DESTDIR=$PKG || exit 1
+
+# Strip binaries and libraries
+( cd $PKG
+ find . | xargs file | grep "executable" | grep ELF | cut -f 1 -d : | xargs strip --strip-unneeded 2> /dev/null || true
+ find . | xargs file | grep "shared object" | grep ELF | cut -f 1 -d : | xargs strip --strip-unneeded 2> /dev/null
+)
+
+
+# Copy program documentation into the package
+# Also, include the SlackBuild script in the documentation directory
+mkdir -p $PKG/usr/doc/$NAME-$VERSION
+cp -a AUTHORS COPYING ChangeLog INSTALL NEWS README \
+$PKG/usr/doc/$NAME-$VERSION
+cat $CWD/$NAME.SlackBuild > $PKG/usr/doc/$NAME-$VERSION/$NAME.SlackBuild
+
+# Copy the slack-desc (and a custom doinst.sh if necessary) into ./install
+mkdir -p $PKG/install
+cat $CWD/data/slack-desc > $PKG/install/slack-desc
+
+# Make the package;
+# If package symlinks need to be created during install *before*
+# your custom contents of doinst.sh runs, then add the -p switch to
+# the makepkg command below -- see makepkg(8) for details
+cd $PKG
+/sbin/makepkg -l y -c n $CWD/$NAME-$VERSION-$ARCH-$BUILD.tgz
+
+# remove unnecessary tmp dir..
+rm -rf $TMP
+
+# echo "done"
+echo "done! Yuppy!!"
+
diff --git a/scripts/codingstyle.sh b/scripts/codingstyle.sh
new file mode 100755
index 00000000..bb3add49
--- /dev/null
+++ b/scripts/codingstyle.sh
@@ -0,0 +1,48 @@
+#!/bin/sh
+#
+# apply rekonq coding style to all cpp and header files in src directory
+#
+# requirements: installed astyle
+#
+# rekonq use kdelibs coding style, except for brackets, so while kdelibs coding style
+# is
+#
+# void foo() {
+# ...
+# }
+#
+# rekonq uses
+#
+# void foo()
+# {
+# ...
+# }
+#
+# I like this way, for me more readable.
+#
+# Kdelibs coding style is defined in http://techbase.kde.org/Policies/Kdelibs_Coding_Style
+
+
+PWD=$(pwd)
+
+cd $PWD
+cd ..
+cd src
+
+echo "Applying astyle rules..."
+astyle \
+--indent=spaces=4 \
+--brackets=break \
+--indent-labels \
+--pad=oper \
+--unpad=paren \
+--one-line=keep-statements \
+--convert-tabs \
+--indent-preprocessor \
+`find -type f -name '*.cpp'` `find -type f -name '*.h'`
+
+echo "Removing .orig files..."
+rm *.orig
+
+echo "Done!"
+
diff --git a/scripts/i18n.sh b/scripts/i18n.sh
new file mode 100755
index 00000000..e9b5444d
--- /dev/null
+++ b/scripts/i18n.sh
@@ -0,0 +1,41 @@
+#! /usr/bin/env bash
+
+BASEDIR="../src/"
+PROJECT="rekonq"
+BUGADDR="http://sourceforge.net/tracker/?group_id=252277&atid=1126949"
+WDIR="../po/"
+
+cd ${BASEDIR}
+echo "Preparing rc files"
+find . -name '*.rc' -o -name '*.ui' -o -name '*.kcfg' | sort > ${WDIR}/rcfiles.list
+xargs --arg-file=${WDIR}/rcfiles.list extractrc > ${WDIR}/rc.cpp
+cd ${WDIR}
+echo "Done preparing rc files"
+
+echo "Extracting messages"
+cd ${BASEDIR}
+find . -name '*.cpp' -o -name '*.h' -o -name '*.c' | sort > ${WDIR}/infiles.list
+echo "rc.cpp" >> ${WDIR}/infiles.list
+cd ${WDIR}
+xgettext --from-code=UTF-8 -C -kde -ci18n -ki18n:1 -ki18nc:1c,2 -ki18np:1,2 -ki18ncp:1c,2,3 -ktr2i18n:1 \
+ -kI18N_NOOP:1 -kI18N_NOOP2:1c,2 -kaliasLocale -kki18n:1 -kki18nc:1c,2 -kki18np:1,2 -kki18ncp:1c,2,3 \
+ --msgid-bugs-address="${BUGADDR}" \
+ --files-from=infiles.list -D ${BASEDIR} -D ${WDIR} -o ${PROJECT}.pot || { echo "error while calling xgettext. aborting."; exit 1; }
+echo "Done extracting messages"
+
+echo "Merging translations"
+catalogs=`find . -name '*.po'`
+for cat in $catalogs; do
+ echo $cat
+ msgmerge -o $cat.new $cat ${PROJECT}.pot
+ mv $cat.new $cat
+done
+echo "Done merging translations"
+
+echo "Cleaning up"
+cd ${WDIR}
+rm rcfiles.list
+rm infiles.list
+rm rc.cpp
+echo "Done"
+
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
new file mode 100644
index 00000000..a64cc747
--- /dev/null
+++ b/src/CMakeLists.txt
@@ -0,0 +1,63 @@
+SET( rekonq_SRCS
+ autosaver.cpp
+ application.cpp
+ mainwindow.cpp
+ mainview.cpp
+ tabbar.cpp
+ cookiejar.cpp
+ edittableview.cpp
+ edittreeview.cpp
+ history.cpp
+ download.cpp
+ bookmarks.cpp
+ modelmenu.cpp
+ networkaccessmanager.cpp
+ urlbar.cpp
+ findbar.cpp
+ searchbar.cpp
+ settings.cpp
+ webview.cpp
+ main.cpp
+ sidepanel.cpp
+ panelhistory.cpp
+ lineedit.cpp
+ stackedurlbar.cpp
+)
+
+KDE4_ADD_UI_FILES( rekonq_SRCS
+ cookies.ui
+ cookiesexceptions.ui
+ history.ui
+ password.ui
+ proxy.ui
+ settings_general.ui
+ settings_fonts.ui
+ settings_privacy.ui
+ settings_proxy.ui
+ settings_webkit.ui
+ )
+
+KDE4_ADD_KCFG_FILES( rekonq_SRCS rekonq.kcfgc )
+
+### ------------------------------------------
+
+ADD_DEFINITIONS( ${KDE4_DEFINITIONS} )
+
+KDE4_ADD_EXECUTABLE( rekonq ${rekonq_SRCS} )
+
+TARGET_LINK_LIBRARIES( rekonq
+ ${QT_LIBRARIES}
+ ${QT_QTNETWORK_LIBRARY}
+ ${QT_QTWEBKIT_LIBRARY}
+ ${QT_QTUITOOLS_LIBRARY}
+ ${KDE4_KUTILS_LIBS}
+ ${KDE4_KDEUI_LIBS}
+ ${KDE4_KIO_LIBS}
+)
+
+INSTALL( TARGETS rekonq ${INSTALL_TARGETS_DEFAULT_ARGS} )
+
+########### install files ###############
+
+INSTALL( FILES rekonq.kcfg DESTINATION ${KCFG_INSTALL_DIR} )
+INSTALL( FILES rekonqui.rc DESTINATION ${DATA_INSTALL_DIR}/rekonq )
diff --git a/src/application.cpp b/src/application.cpp
new file mode 100644
index 00000000..ec24691e
--- /dev/null
+++ b/src/application.cpp
@@ -0,0 +1,206 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Self Includes
+#include "application.h"
+#include "application.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "mainwindow.h"
+#include "cookiejar.h"
+#include "history.h"
+#include "networkaccessmanager.h"
+#include "mainview.h"
+#include "webview.h"
+#include "download.h"
+
+// KDE Includes
+#include <KCmdLineArgs>
+#include <KAboutData>
+#include <KStandardDirs>
+#include <KConfig>
+#include <kio/job.h>
+#include <kio/jobclasses.h>
+
+// Qt Includes
+#include <QtCore>
+#include <QtWebKit>
+
+
+QPointer<HistoryManager> Application::s_historyManager;
+QPointer<NetworkAccessManager> Application::s_networkAccessManager;
+QPointer<DownloadManager> Application::s_downloadManager;
+QPointer<BookmarkProvider> Application::s_bookmarkProvider;
+
+
+
+Application::Application()
+ : KUniqueApplication()
+{
+}
+
+
+Application::~Application()
+{
+ delete m_mainWindow;
+ delete s_bookmarkProvider;
+ delete s_networkAccessManager;
+ delete s_historyManager;
+}
+
+
+int Application::newInstance()
+{
+ KCmdLineArgs::setCwd(QDir::currentPath().toUtf8());
+ KCmdLineArgs* args = KCmdLineArgs::parsedArgs();
+
+ if (!m_mainWindow)
+ {
+ m_mainWindow = new MainWindow();
+
+ m_mainWindow->setObjectName("MainWindow");
+ setWindowIcon(KIcon("rekonq"));
+
+ m_mainWindow->show();
+
+ QTimer::singleShot(0, this, SLOT(postLaunch()));
+ }
+
+ if (args->count() > 0)
+ {
+ for (int i = 0; i < args->count(); ++i)
+ {
+ KUrl url = MainWindow::guessUrlFromString(args->arg(i));
+ newWebView();
+ mainWindow()->loadUrl(url);
+ }
+ args->clear();
+ }
+ else
+ {
+ newWebView();
+ mainWindow()->slotHome();
+ }
+
+ return 0;
+}
+
+
+Application *Application::instance()
+{
+ return (static_cast<Application *>(QCoreApplication::instance()));
+}
+
+
+void Application::postLaunch()
+{
+ // set Icon Database Path to store "favicons" associated with web sites
+ QString directory = KStandardDirs::locateLocal("cache" , "" , true);
+ if (directory.isEmpty())
+ {
+ directory = QDir::homePath() + QLatin1String("/.") + QCoreApplication::applicationName();
+ }
+ QWebSettings::setIconDatabasePath(directory);
+
+ Application::historyManager();
+}
+
+
+
+void Application::slotSaveConfiguration() const
+{
+ ReKonfig::self()->writeConfig();
+}
+
+
+MainWindow *Application::mainWindow()
+{
+ return m_mainWindow;
+}
+
+
+WebView *Application::newWebView(Rekonq::OpenType type)
+{
+ return m_mainWindow->mainView()->newWebView(type);
+}
+
+
+CookieJar *Application::cookieJar()
+{
+ return (CookieJar*)networkAccessManager()->cookieJar();
+}
+
+
+NetworkAccessManager *Application::networkAccessManager()
+{
+ if (!s_networkAccessManager)
+ {
+ s_networkAccessManager = new NetworkAccessManager();
+ s_networkAccessManager->setCookieJar(new CookieJar);
+ }
+ return s_networkAccessManager;
+}
+
+
+HistoryManager *Application::historyManager()
+{
+ if (!s_historyManager)
+ {
+ s_historyManager = new HistoryManager();
+ QWebHistoryInterface::setDefaultInterface(s_historyManager);
+ }
+ return s_historyManager;
+}
+
+
+DownloadManager *Application::downloadManager()
+{
+ if (!s_downloadManager)
+ {
+ s_downloadManager = new DownloadManager();
+ }
+ return s_downloadManager;
+}
+
+
+BookmarkProvider *Application::bookmarkProvider()
+{
+ if (!s_bookmarkProvider)
+ {
+ s_bookmarkProvider = new BookmarkProvider();
+ }
+ return s_bookmarkProvider;
+}
+
+
+KIcon Application::icon(const KUrl &url) const
+{
+ KIcon icon = KIcon(QWebSettings::iconForUrl(url));
+ if (icon.isNull())
+ {
+ icon = KIcon("kde");
+ }
+ return icon;
+}
diff --git a/src/application.h b/src/application.h
new file mode 100644
index 00000000..61f4af81
--- /dev/null
+++ b/src/application.h
@@ -0,0 +1,115 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef APPLICATION_H
+#define APPLICATION_H
+
+// Qt Includes
+#include <QPointer>
+
+// KDE Includes
+#include <KUniqueApplication>
+#include <KCmdLineArgs>
+#include <KIcon>
+#include <KUrl>
+#include <KJob>
+#include <kio/job.h>
+#include <kio/jobclasses.h>
+
+
+// Forward Declarations
+class KIcon;
+class KUrl;
+class BookmarkProvider;
+class CookieJar;
+class DownloadManager;
+class HistoryManager;
+class MainWindow;
+class NetworkAccessManager;
+class WebView;
+
+
+namespace Rekonq
+{
+ /**
+ * @short Open link options
+ * Different modes of opening new tab
+ */
+ enum OpenType
+ {
+ Default, ///< open url according to users settings
+ New, ///< open url in new tab and make it current
+ Background ///< open url in new tab in background
+ };
+}
+
+
+/**
+ *
+ */
+class Application : public KUniqueApplication
+{
+ Q_OBJECT
+
+public:
+ Application();
+ ~Application();
+ int newInstance();
+ static Application *instance();
+
+ MainWindow *mainWindow();
+ WebView* newWebView(Rekonq::OpenType type = Rekonq::Default);
+
+ KIcon icon(const KUrl &url) const;
+
+ static HistoryManager *historyManager();
+ static CookieJar *cookieJar();
+ static NetworkAccessManager *networkAccessManager();
+ static DownloadManager *downloadManager();
+ static BookmarkProvider *bookmarkProvider();
+
+public slots:
+ /**
+ * Save application's configuration
+ * @see ReKonfig::self()->writeConfig();
+ */
+ void slotSaveConfiguration() const;
+
+
+private slots:
+
+ /**
+ * Any actions that can be delayed until the window is visible
+ */
+ void postLaunch();
+
+
+private:
+ static QPointer<HistoryManager> s_historyManager;
+ static QPointer<NetworkAccessManager> s_networkAccessManager;
+ static QPointer<DownloadManager> s_downloadManager;
+ static QPointer<BookmarkProvider> s_bookmarkProvider;
+
+ QPointer<MainWindow> m_mainWindow;
+};
+
+#endif // APPLICATION_H
diff --git a/src/autosaver.cpp b/src/autosaver.cpp
new file mode 100644
index 00000000..25bf9016
--- /dev/null
+++ b/src/autosaver.cpp
@@ -0,0 +1,90 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Local Includes
+#include "autosaver.h"
+
+// KDE Includes
+#include <KDebug>
+
+// Qt Includes
+#include <QtCore>
+
+
+#define AUTOSAVE_IN 1000 * 3 // seconds
+#define MAXWAIT 1000 * 15 // seconds
+
+
+AutoSaver::AutoSaver(QObject *parent) : QObject(parent)
+{
+ Q_ASSERT(parent);
+}
+
+
+AutoSaver::~AutoSaver()
+{
+ if (m_timer.isActive())
+ kWarning() << "AutoSaver: still active when destroyed, changes not saved.";
+}
+
+
+void AutoSaver::changeOccurred()
+{
+ if (m_firstChange.isNull())
+ m_firstChange.start();
+
+ if (m_firstChange.elapsed() > MAXWAIT)
+ {
+ saveIfNeccessary();
+ }
+ else
+ {
+ m_timer.start(AUTOSAVE_IN, this);
+ }
+}
+
+
+void AutoSaver::timerEvent(QTimerEvent *event)
+{
+ if (event->timerId() == m_timer.timerId())
+ {
+ saveIfNeccessary();
+ }
+ else
+ {
+ QObject::timerEvent(event);
+ }
+}
+
+
+void AutoSaver::saveIfNeccessary()
+{
+ if (!m_timer.isActive())
+ return;
+ m_timer.stop();
+ m_firstChange = QTime();
+ if (!QMetaObject::invokeMethod(parent(), "save", Qt::DirectConnection))
+ {
+ kWarning() << "AutoSaver: error invoking slot save() on parent";
+ }
+}
+
diff --git a/src/autosaver.h b/src/autosaver.h
new file mode 100644
index 00000000..8931da13
--- /dev/null
+++ b/src/autosaver.h
@@ -0,0 +1,55 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef AUTOSAVER_H
+#define AUTOSAVER_H
+
+#include <QtCore>
+
+/*
+ This class will call the save() slot on the parent object when the parent changes.
+ It will wait several seconds after changed() to combining multiple changes and
+ prevent continuous writing to disk.
+ */
+class AutoSaver : public QObject
+{
+ Q_OBJECT
+
+public:
+ AutoSaver(QObject *parent);
+ ~AutoSaver();
+ void saveIfNeccessary();
+
+public slots:
+ void changeOccurred();
+
+protected:
+ void timerEvent(QTimerEvent *event);
+
+private:
+ QBasicTimer m_timer;
+ QTime m_firstChange;
+
+};
+
+#endif // AUTOSAVER_H
+
diff --git a/src/bookmarks.cpp b/src/bookmarks.cpp
new file mode 100644
index 00000000..c7f4da98
--- /dev/null
+++ b/src/bookmarks.cpp
@@ -0,0 +1,278 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Self Includes
+#include "bookmarks.h"
+#include "bookmarks.moc"
+
+// Local Includes
+#include "mainwindow.h"
+#include "webview.h"
+#include "application.h"
+
+// KDE Includes
+#include <KActionCollection>
+#include <KBookmark>
+#include <KBookmarkAction>
+#include <KBookmarkActionMenu>
+#include <KBookmarkGroup>
+#include <KBookmarkMenu>
+#include <KToolBar>
+#include <KDebug>
+#include <KMenu>
+#include <KMimeType>
+#include <KStandardDirs>
+#include <KUrl>
+
+// Qt Includes
+#include <QActionGroup>
+#include <QFile>
+
+
+BookmarkOwner::BookmarkOwner(QObject *parent)
+ : QObject(parent)
+ , KBookmarkOwner()
+{
+}
+
+
+void BookmarkOwner::openBookmark(const KBookmark & bookmark,
+ Qt::MouseButtons mouseButtons,
+ Qt::KeyboardModifiers keyboardModifiers)
+{
+ Q_UNUSED(mouseButtons)
+ Q_UNUSED(keyboardModifiers)
+
+ emit openUrl(bookmark.url());
+}
+
+
+QString BookmarkOwner::currentUrl() const
+{
+ return Application::instance()->mainWindow()->currentTab()->url().url();
+}
+
+
+QString BookmarkOwner::currentTitle() const
+{
+ return Application::instance()->mainWindow()->currentTab()->title();
+}
+
+
+void BookmarkOwner::openFolderinTabs(const KBookmarkGroup &bm)
+{
+ QList<KUrl> urlList = bm.groupUrlList();
+ QList<KUrl>::iterator url;
+ Application* app = Application::instance();
+ for (url = urlList.begin(); url != urlList.end(); ++url)
+ {
+ app->newWebView();
+ app->mainWindow()->loadUrl(*url);
+ }
+}
+
+
+// ------------------------------------------------------------------------------------------------------
+
+
+BookmarkMenu::BookmarkMenu(KBookmarkManager *manager,
+ KBookmarkOwner *owner,
+ KMenu *menu,
+ KActionCollection* actionCollection)
+ : KBookmarkMenu(manager, owner, menu, actionCollection)
+
+{
+ actionCollection->addAction(KStandardAction::AddBookmark,
+ QLatin1String("add_bookmark_payload"),
+ this, SLOT(slotAddBookmark()));
+
+}
+
+BookmarkMenu::~BookmarkMenu()
+{
+}
+
+
+KMenu *BookmarkMenu::viewContextMenu(QAction *action)
+{
+ return contextMenu(action);
+}
+
+
+void BookmarkMenu::slotAddBookmark()
+{
+ KAction *action = qobject_cast<KAction *>(sender());
+ if (action && !action->data().isNull())
+ {
+ KBookmarkGroup parentBookmark = manager()->findByAddress(parentAddress()).toGroup();
+ /// TODO Add bookmark Icon
+ parentBookmark.addBookmark(owner()->currentTitle(), action->data().toUrl());
+ manager()->emitChanged();
+ return;
+ }
+
+ KBookmarkMenu::slotAddBookmark();
+}
+
+
+// ------------------------------------------------------------------------------------------------------
+
+
+BookmarkProvider::BookmarkProvider(QWidget *parent)
+ : QWidget(parent)
+ , m_manager(0)
+ , m_owner(0)
+ , m_menu(new KMenu(this))
+ , m_actionCollection(new KActionCollection(this))
+ , m_bookmarkMenu(0)
+ , m_bookmarkToolBar(0)
+{
+ KUrl bookfile = KUrl("~/.kde/share/apps/konqueror/bookmarks.xml"); // share konqueror bookmarks
+
+ if (!QFile::exists(bookfile.path()))
+ {
+ bookfile = KUrl("~/.kde4/share/apps/konqueror/bookmarks.xml");
+ if (!QFile::exists(bookfile.path()))
+ {
+ QString bookmarksDefaultPath = KStandardDirs::locate("appdata" , "defaultbookmarks.xbel");
+ kWarning() << bookmarksDefaultPath;
+ QFile bkms(bookmarksDefaultPath);
+ QString bookmarksPath = KStandardDirs::locateLocal("appdata", "bookmarks.xml", true);
+ bookmarksPath.replace("rekonq", "konqueror");
+ bkms.copy(bookmarksPath);
+
+ bookfile = KUrl(bookmarksPath);
+ }
+ }
+ m_manager = KBookmarkManager::managerForExternalFile(bookfile.path());
+ connect(m_manager, SIGNAL(changed(const QString &, const QString &)),
+ this, SLOT(slotBookmarksChanged(const QString &, const QString &)));
+
+ // setup menu
+ m_owner = new BookmarkOwner(this);
+ connect(m_owner, SIGNAL(openUrl(const KUrl&)), this, SIGNAL(openUrl(const KUrl&)));
+ m_bookmarkMenu = new BookmarkMenu(m_manager, m_owner, m_menu, m_actionCollection);
+
+ // setup toolbar
+ setupToolBar();
+}
+
+
+BookmarkProvider::~BookmarkProvider()
+{
+ delete m_bookmarkToolBar;
+ delete m_bookmarkMenu;
+ delete m_actionCollection;
+ delete m_menu;
+ delete m_owner;
+ delete m_manager;
+}
+
+
+void BookmarkProvider::setupToolBar()
+{
+ m_bookmarkToolBar = new KToolBar(this);
+ m_bookmarkToolBar->setToolButtonStyle(Qt::ToolButtonTextBesideIcon);
+ m_bookmarkToolBar->setIconDimensions(16);
+ m_bookmarkToolBar->setAcceptDrops(true);
+ m_bookmarkToolBar->setContentsMargins(0, 0, 0, 0);
+ m_bookmarkToolBar->setMinimumHeight(16);
+ m_bookmarkToolBar->setContextMenuPolicy(Qt::CustomContextMenu);
+ connect(m_bookmarkToolBar, SIGNAL(customContextMenuRequested(const QPoint &)),
+ this, SLOT(contextMenu(const QPoint &)));
+
+ slotBookmarksChanged("", "");
+}
+
+
+void BookmarkProvider::slotBookmarksChanged(const QString &group, const QString &caller)
+{
+ Q_UNUSED(group)
+ Q_UNUSED(caller)
+
+ if (!m_bookmarkToolBar)
+ {
+ kWarning() << "There is no bookmark toolbar";
+ return;
+ }
+
+ KActionCollection bookmarkCollection(this);
+
+ KBookmarkGroup toolBarGroup = m_manager->toolbar();
+ if (toolBarGroup.isNull())
+ return;
+
+ KBookmark bookmark = toolBarGroup.first();
+ while (!bookmark.isNull())
+ {
+ if (!bookmark.isGroup())
+ {
+ KAction *action = new KBookmarkAction(bookmark, m_owner, this);
+ QString text = bookmark.address();
+ bookmarkCollection.addAction(text, action);
+ }
+ bookmark = toolBarGroup.next(bookmark);
+ }
+ m_bookmarkToolBar->clear();
+ m_bookmarkToolBar->addActions(bookmarkCollection.actions());
+}
+
+
+QAction *BookmarkProvider::actionByName(const QString &name)
+{
+ QAction *action = m_actionCollection->action(name);
+ if (action)
+ return action;
+ /* else */
+ kWarning() << "Action named: " << name << " not found, returning empty action.";
+ return new QAction(this); // return empty object instead of NULL pointer
+}
+
+
+void BookmarkProvider::contextMenu(const QPoint &point)
+{
+ KAction* action = dynamic_cast<KAction*>(m_bookmarkToolBar->actionAt(point));
+ if (!action)
+ return;
+ KMenu *menu = m_bookmarkMenu->viewContextMenu(action);
+ menu->popup(m_bookmarkToolBar->mapToGlobal(point));
+}
+
+
+KActionMenu* BookmarkProvider::bookmarkActionMenu()
+{
+ KActionMenu *bookmarkActionMenu = new KActionMenu(this);
+ bookmarkActionMenu->setMenu(m_menu);
+ bookmarkActionMenu->setText(i18n("&Bookmarks"));
+ return bookmarkActionMenu;
+}
+
+
+KAction* BookmarkProvider::bookmarkToolBarAction()
+{
+ KAction *bookmarkToolBarAction = new KAction(this);
+ bookmarkToolBarAction->setDefaultWidget(m_bookmarkToolBar); // The ownership is transferred to action
+ bookmarkToolBarAction->setText(i18n("Bookmarks Bar"));
+ bookmarkToolBarAction->setShortcutConfigurable(false);
+ return bookmarkToolBarAction;
+}
+
diff --git a/src/bookmarks.h b/src/bookmarks.h
new file mode 100644
index 00000000..d7213cb7
--- /dev/null
+++ b/src/bookmarks.h
@@ -0,0 +1,238 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef BOOKMARKS_H
+#define BOOKMARKS_H
+
+// Qt Includes
+#include <QWidget>
+
+// KDE Includes
+#include <KBookmarkOwner>
+
+// Forward Declarations
+class BookmarkProvider;
+
+class KAction;
+class KActionCollection;
+class KActionMenu;
+class KUrl;
+class KToolBar;
+class KBookmarkManager;
+
+
+/**
+ * Reimplementation of KBookmarkOwner, this class allows to manage
+ * bookmarks as actions
+ *
+ */
+class BookmarkOwner : public QObject , public KBookmarkOwner
+{
+ Q_OBJECT
+
+public:
+
+ /**
+ * @short The class constructor.
+ *
+ * @param parent the pointer parent Bookmark provider. We need it
+ * to get pointer to MainWindow
+ */
+ BookmarkOwner(QObject *parent = 0);
+ virtual ~BookmarkOwner() {}
+
+ /**
+ * This function is called when a bookmark is selected and belongs to
+ * the ancestor class.
+ * This method actually emits signal to load bookmark's url.
+ *
+ * @param bookmark the bookmark to open
+ * @param mouseButtons the mouse buttons clicked to select the bookmark
+ * @param keyboardModifiers the keyboard modifiers pushed when the bookmark was selected
+ */
+ virtual void openBookmark(const KBookmark &bookmark,
+ Qt::MouseButtons mouseButtons,
+ Qt::KeyboardModifiers keyboardModifiers);
+
+
+ /**
+ * this method, from KBookmarkOwner interface, allows to add the current page
+ * to the bookmark list, returning the URL page as QString.
+ *
+ * @return the current page's URL
+ */
+ virtual QString currentUrl() const;
+
+ /**
+ * this method, from KBookmarkOwner interface, allows to add the current page
+ * to the bookmark list, returning the title's page as QString.
+ *
+ * @return the current page's title
+ */
+ virtual QString currentTitle() const;
+
+ /**
+ * This function returns whether the owner supports tabs.
+ */
+ virtual bool supportsTabs() const
+ {
+ return true;
+ }
+
+ /**
+ * Called if the user wants to open every bookmark in this folder in a new tab.
+ * The default implementation does nothing.
+ * This is only called if supportsTabs() returns true
+ */
+ virtual void openFolderinTabs(const KBookmarkGroup &bm);
+
+signals:
+ /**
+ * This signal is emitted when an url has to be loaded
+ *
+ * @param url the URL to load
+ *
+ */
+ void openUrl(const KUrl &);
+
+private:
+
+};
+
+// ------------------------------------------------------------------------------
+
+
+#include <KBookmarkMenu>
+
+
+/**
+ * This class represent the rekonq bookmarks menu.
+ * It's just a simple class inherited from KBookmarkMenu
+ *
+ */
+class BookmarkMenu : public KBookmarkMenu
+{
+ Q_OBJECT
+
+public:
+ BookmarkMenu(KBookmarkManager* manager,
+ KBookmarkOwner* owner,
+ KMenu* menu,
+ KActionCollection* actionCollection);
+ ~BookmarkMenu();
+
+ virtual KMenu *viewContextMenu(QAction* action);
+
+protected slots:
+ void slotAddBookmark();
+
+};
+
+
+// ------------------------------------------------------------------------------
+
+
+/**
+ * This class represent the interface to rekonq bookmarks system.
+ * All rekonq needs (Bookmarks Menu, Bookmarks Toolbar) is provided
+ * from this class.
+ * So it implements code to have each one
+ *
+ *
+ */
+class BookmarkProvider : public QWidget
+{
+ Q_OBJECT
+
+public:
+ /**
+ * @short Class constructor.
+ * Connect BookmarksProvider with bookmarks source
+ * (actually konqueror's bookmarks)
+ * @param parent The MainWindow to provide bookmarks objects
+ *
+ */
+ BookmarkProvider(QWidget* parent = 0);
+ ~BookmarkProvider();
+
+ /**
+ * @short Get the Bookmarks Menu Action
+ * @return the Bookmarks Menu
+ */
+ KActionMenu *bookmarkActionMenu();
+
+
+ /**
+ * @short Get the Bookmarks Toolbar Action
+ * @return the Bookmarks Toolbar Action
+ */
+ KAction *bookmarkToolBarAction();
+
+
+ /**
+ * @short Get action by name
+ * This method returns poiner bookmark action of given name.
+ * @pre m_actionCollection != NULL
+ * @param name Name of action you want to get
+ * @return It returns actions if one exists or empty object
+ */
+ QAction *actionByName(const QString &name);
+
+signals:
+ /**
+ * @short This signal is emitted when an url has to be loaded
+ *
+ * @param url the URL to load
+ */
+ void openUrl(const KUrl &url);
+
+
+public slots:
+ /**
+ * @short Opens the context menu on given position
+ * @param point Point on whitch you want to open this menu
+ */
+ void contextMenu(const QPoint &point);
+
+ /**
+ * @short Waits for signal that the group with the address has been modified by the caller.
+ * Waits for signal that the group (or any of its children) with the address
+ * @p groupAddress (e.g. "/4/5") has been modified by the caller @p caller.
+ *
+ * @param group bookmark group adress
+ * @param caller caller that modified the bookmarks
+ * @see KBookmarkManager::changed
+ */
+ void slotBookmarksChanged(const QString &group, const QString &caller);
+
+private:
+ void setupToolBar();
+
+ KBookmarkManager *m_manager;
+ BookmarkOwner *m_owner;
+ KMenu *m_menu;
+ KActionCollection *m_actionCollection;
+ BookmarkMenu *m_bookmarkMenu;
+ KToolBar *m_bookmarkToolBar;
+};
+
+#endif
diff --git a/src/cookiejar.cpp b/src/cookiejar.cpp
new file mode 100644
index 00000000..de7d7d7e
--- /dev/null
+++ b/src/cookiejar.cpp
@@ -0,0 +1,841 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Self Includes
+#include "cookiejar.h"
+#include "cookiejar.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "autosaver.h"
+
+// KDE Includes
+#include <KConfig>
+#include <KStandardDirs>
+#include <KDebug>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+#include <QtWebKit>
+
+
+static const unsigned int JAR_VERSION = 23;
+
+
+QDataStream &operator<<(QDataStream &stream, const QList<QNetworkCookie> &list)
+{
+ stream << JAR_VERSION;
+ stream << quint32(list.size());
+ for (int i = 0; i < list.size(); ++i)
+ stream << list.at(i).toRawForm();
+ return stream;
+}
+
+
+QDataStream &operator>>(QDataStream &stream, QList<QNetworkCookie> &list)
+{
+ list.clear();
+
+ quint32 version;
+ stream >> version;
+
+ if (version != JAR_VERSION)
+ return stream;
+
+ quint32 count;
+ stream >> count;
+ for (quint32 i = 0; i < count; ++i)
+ {
+ QByteArray value;
+ stream >> value;
+ QList<QNetworkCookie> newCookies = QNetworkCookie::parseCookies(value);
+ if (newCookies.count() == 0 && value.length() != 0)
+ {
+ kWarning() << "CookieJar: Unable to parse saved cookie:" << value;
+ }
+ for (int j = 0; j < newCookies.count(); ++j)
+ list.append(newCookies.at(j));
+ if (stream.atEnd())
+ break;
+ }
+ return stream;
+}
+
+
+CookieJar::CookieJar(QObject *parent)
+ : QNetworkCookieJar(parent)
+ , m_loaded(false)
+ , m_saveTimer(new AutoSaver(this))
+ , m_acceptCookies(AcceptOnlyFromSitesNavigatedTo)
+{
+ load();
+}
+
+
+CookieJar::~CookieJar()
+{
+ if (m_keepCookies == KeepUntilExit)
+ clear();
+ m_saveTimer->saveIfNeccessary();
+}
+
+
+void CookieJar::clear()
+{
+ setAllCookies(QList<QNetworkCookie>());
+ m_saveTimer->changeOccurred();
+ emit cookiesChanged();
+}
+
+
+void CookieJar::load()
+{
+ if (m_loaded)
+ return;
+
+ // load cookies and exceptions
+ QString filepath = KStandardDirs::locateLocal("appdata", "cookies.ini");
+ qRegisterMetaTypeStreamOperators<QList<QNetworkCookie> >("QList<QNetworkCookie>");
+ QSettings cookieSettings(filepath, QSettings::IniFormat);
+ setAllCookies(qvariant_cast<QList<QNetworkCookie> >(cookieSettings.value(QLatin1String("cookies"))));
+ cookieSettings.beginGroup(QLatin1String("Exceptions"));
+ m_exceptions_block = cookieSettings.value(QLatin1String("block")).toStringList();
+ m_exceptions_allow = cookieSettings.value(QLatin1String("allow")).toStringList();
+ m_exceptions_allowForSession = cookieSettings.value(QLatin1String("allowForSession")).toStringList();
+ qSort(m_exceptions_block.begin(), m_exceptions_block.end());
+ qSort(m_exceptions_allow.begin(), m_exceptions_allow.end());
+ qSort(m_exceptions_allowForSession.begin(), m_exceptions_allowForSession.end());
+
+ loadSettings();
+
+ save();
+}
+
+
+void CookieJar::loadSettings()
+{
+ int canAcceptCookies = ReKonfig::acceptCookies();
+
+ switch (canAcceptCookies)
+ {
+ case 0:
+ m_acceptCookies = AcceptAlways;
+ break;
+ case 1:
+ m_acceptCookies = AcceptNever;
+ break;
+ case 2:
+ default:
+ m_acceptCookies = AcceptOnlyFromSitesNavigatedTo;
+ break;
+ }
+
+ int canKeepCookiesUntil = ReKonfig::keepCookiesUntil();
+
+ switch (canKeepCookiesUntil)
+ {
+ default:
+ case 0:
+ m_keepCookies = KeepUntilExpire;
+ break;
+ case 1:
+ m_keepCookies = KeepUntilExit;
+ setAllCookies(QList<QNetworkCookie>());
+ break;
+ case 2:
+ m_keepCookies = KeepUntilTimeLimit;
+ break;
+ }
+
+ m_loaded = true;
+ emit cookiesChanged();
+}
+
+
+void CookieJar::save()
+{
+ if (!m_loaded)
+ return;
+ purgeOldCookies();
+
+ QString filepath = KStandardDirs::locateLocal("appdata", "cookies.ini");
+ QSettings cookieSettings(filepath, QSettings::IniFormat);
+ QList<QNetworkCookie> cookies = allCookies();
+ for (int i = cookies.count() - 1; i >= 0; --i)
+ {
+ if (cookies.at(i).isSessionCookie())
+ cookies.removeAt(i);
+ }
+
+ cookieSettings.setValue(QLatin1String("cookies"), qVariantFromValue<QList<QNetworkCookie> >(cookies));
+ cookieSettings.beginGroup(QLatin1String("Exceptions"));
+ cookieSettings.setValue(QLatin1String("block"), m_exceptions_block);
+ cookieSettings.setValue(QLatin1String("allow"), m_exceptions_allow);
+ cookieSettings.setValue(QLatin1String("allowForSession"), m_exceptions_allowForSession);
+
+ // save cookie settings
+ int n;
+ switch (m_acceptCookies)
+ {
+ case AcceptAlways:
+ n = 0;
+ break;
+ case AcceptNever:
+ n = 1;
+ break;
+ case AcceptOnlyFromSitesNavigatedTo:
+ default:
+ n = 2;
+ break;
+ }
+ ReKonfig::setAcceptCookies(n);
+
+
+ switch (m_keepCookies)
+ {
+ default:
+ case KeepUntilExpire:
+ n = 0;
+ break;
+ case KeepUntilExit:
+ n = 1;
+ break;
+ case KeepUntilTimeLimit:
+ n = 2;
+ break;
+ }
+ ReKonfig::setKeepCookiesUntil(n);
+}
+
+
+void CookieJar::purgeOldCookies()
+{
+ QList<QNetworkCookie> cookies = allCookies();
+ if (cookies.isEmpty())
+ return;
+ int oldCount = cookies.count();
+ QDateTime now = QDateTime::currentDateTime();
+ for (int i = cookies.count() - 1; i >= 0; --i)
+ {
+ if (!cookies.at(i).isSessionCookie() && cookies.at(i).expirationDate() < now)
+ cookies.removeAt(i);
+ }
+ if (oldCount == cookies.count())
+ return;
+ setAllCookies(cookies);
+ emit cookiesChanged();
+}
+
+
+QList<QNetworkCookie> CookieJar::cookiesForUrl(const QUrl &url) const
+{
+ CookieJar *that = const_cast<CookieJar*>(this);
+ if (!m_loaded)
+ that->load();
+
+ QWebSettings *globalSettings = QWebSettings::globalSettings();
+ if (globalSettings->testAttribute(QWebSettings::PrivateBrowsingEnabled))
+ {
+ QList<QNetworkCookie> noCookies;
+ return noCookies;
+ }
+
+ return QNetworkCookieJar::cookiesForUrl(url);
+}
+
+
+bool CookieJar::setCookiesFromUrl(const QList<QNetworkCookie> &cookieList, const QUrl &url)
+{
+ if (!m_loaded)
+ load();
+
+ QWebSettings *globalSettings = QWebSettings::globalSettings();
+ if (globalSettings->testAttribute(QWebSettings::PrivateBrowsingEnabled))
+ return false;
+
+ QString host = url.host();
+ bool eBlock = qBinaryFind(m_exceptions_block.begin(), m_exceptions_block.end(), host) != m_exceptions_block.end();
+ bool eAllow = qBinaryFind(m_exceptions_allow.begin(), m_exceptions_allow.end(), host) != m_exceptions_allow.end();
+ bool eAllowSession = qBinaryFind(m_exceptions_allowForSession.begin(), m_exceptions_allowForSession.end(), host) != m_exceptions_allowForSession.end();
+
+ bool addedCookies = false;
+ // pass exceptions
+ bool acceptInitially = (m_acceptCookies != AcceptNever);
+ if ((acceptInitially && !eBlock) || (!acceptInitially && (eAllow || eAllowSession)))
+ {
+ // pass url domain == cookie domain
+ QDateTime soon = QDateTime::currentDateTime();
+ soon = soon.addDays(90);
+ foreach(QNetworkCookie cookie, cookieList)
+ {
+ QList<QNetworkCookie> lst;
+ if (m_keepCookies == KeepUntilTimeLimit
+ && !cookie.isSessionCookie()
+ && cookie.expirationDate() > soon)
+ {
+ cookie.setExpirationDate(soon);
+ }
+ lst += cookie;
+ if (QNetworkCookieJar::setCookiesFromUrl(lst, url))
+ {
+ addedCookies = true;
+ }
+ else
+ {
+ // finally force it in if wanted
+ if (m_acceptCookies == AcceptAlways)
+ {
+ QList<QNetworkCookie> cookies = allCookies();
+ cookies += cookie;
+ setAllCookies(cookies);
+ addedCookies = true;
+ }
+#if 0
+ else
+ kWarning() << "setCookiesFromUrl failed" << url << cookieList.value(0).toRawForm();
+#endif
+ }
+ }
+ }
+
+ if (addedCookies)
+ {
+ m_saveTimer->changeOccurred();
+ emit cookiesChanged();
+ }
+ return addedCookies;
+}
+
+
+CookieJar::AcceptPolicy CookieJar::acceptPolicy() const
+{
+ if (!m_loaded)
+ (const_cast<CookieJar*>(this))->load();
+ return m_acceptCookies;
+}
+
+
+void CookieJar::setAcceptPolicy(AcceptPolicy policy)
+{
+ if (!m_loaded)
+ load();
+ if (policy == m_acceptCookies)
+ return;
+ m_acceptCookies = policy;
+ m_saveTimer->changeOccurred();
+}
+
+
+CookieJar::KeepPolicy CookieJar::keepPolicy() const
+{
+ if (!m_loaded)
+ (const_cast<CookieJar*>(this))->load();
+ return m_keepCookies;
+}
+
+
+void CookieJar::setKeepPolicy(KeepPolicy policy)
+{
+ if (!m_loaded)
+ load();
+ if (policy == m_keepCookies)
+ return;
+ m_keepCookies = policy;
+ m_saveTimer->changeOccurred();
+}
+
+
+QStringList CookieJar::blockedCookies() const
+{
+ if (!m_loaded)
+ (const_cast<CookieJar*>(this))->load();
+ return m_exceptions_block;
+}
+
+
+QStringList CookieJar::allowedCookies() const
+{
+ if (!m_loaded)
+ (const_cast<CookieJar*>(this))->load();
+ return m_exceptions_allow;
+}
+
+
+QStringList CookieJar::allowForSessionCookies() const
+{
+ if (!m_loaded)
+ (const_cast<CookieJar*>(this))->load();
+ return m_exceptions_allowForSession;
+}
+
+
+void CookieJar::setBlockedCookies(const QStringList &list)
+{
+ if (!m_loaded)
+ load();
+ m_exceptions_block = list;
+ qSort(m_exceptions_block.begin(), m_exceptions_block.end());
+ m_saveTimer->changeOccurred();
+}
+
+
+void CookieJar::setAllowedCookies(const QStringList &list)
+{
+ if (!m_loaded)
+ load();
+ m_exceptions_allow = list;
+ qSort(m_exceptions_allow.begin(), m_exceptions_allow.end());
+ m_saveTimer->changeOccurred();
+}
+
+
+void CookieJar::setAllowForSessionCookies(const QStringList &list)
+{
+ if (!m_loaded)
+ load();
+ m_exceptions_allowForSession = list;
+ qSort(m_exceptions_allowForSession.begin(), m_exceptions_allowForSession.end());
+ m_saveTimer->changeOccurred();
+}
+
+
+// -------------------------------------------------------------------------------------------
+
+
+CookieModel::CookieModel(CookieJar *cookieJar, QObject *parent)
+ : QAbstractTableModel(parent)
+ , m_cookieJar(cookieJar)
+{
+ connect(m_cookieJar, SIGNAL(cookiesChanged()), this, SLOT(cookiesChanged()));
+ m_cookieJar->load();
+}
+
+
+QVariant CookieModel::headerData(int section, Qt::Orientation orientation, int role) const
+{
+ if (role == Qt::SizeHintRole)
+ {
+ QFont font;
+ font.setPointSize(10);
+ QFontMetrics fm(font);
+ int height = fm.height() + fm.height() / 3;
+ int width = fm.width(headerData(section, orientation, Qt::DisplayRole).toString());
+ return QSize(width, height);
+ }
+
+ if (orientation == Qt::Horizontal)
+ {
+ if (role != Qt::DisplayRole)
+ return QVariant();
+
+ switch (section)
+ {
+ case 0:
+ return i18n("Website");
+ case 1:
+ return i18n("Name");
+ case 2:
+ return i18n("Path");
+ case 3:
+ return i18n("Secure");
+ case 4:
+ return i18n("Expires");
+ case 5:
+ return i18n("Contents");
+ default:
+ return QVariant();
+ }
+ }
+ return QAbstractTableModel::headerData(section, orientation, role);
+}
+
+
+QVariant CookieModel::data(const QModelIndex &index, int role) const
+{
+ QList<QNetworkCookie> lst;
+ if (m_cookieJar)
+ lst = m_cookieJar->allCookies();
+ if (index.row() < 0 || index.row() >= lst.size())
+ return QVariant();
+
+ switch (role)
+ {
+ case Qt::DisplayRole:
+ case Qt::EditRole:
+ {
+ QNetworkCookie cookie = lst.at(index.row());
+ switch (index.column())
+ {
+ case 0:
+ return cookie.domain();
+ case 1:
+ return cookie.name();
+ case 2:
+ return cookie.path();
+ case 3:
+ return cookie.isSecure();
+ case 4:
+ return cookie.expirationDate();
+ case 5:
+ return cookie.value();
+ }
+ }
+ case Qt::FontRole:
+ {
+ QFont font;
+ font.setPointSize(10);
+ return font;
+ }
+ }
+
+ return QVariant();
+}
+
+
+int CookieModel::columnCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : 6;
+}
+
+
+int CookieModel::rowCount(const QModelIndex &parent) const
+{
+ return (parent.isValid() || !m_cookieJar) ? 0 : m_cookieJar->allCookies().count();
+}
+
+
+bool CookieModel::removeRows(int row, int count, const QModelIndex &parent)
+{
+ if (parent.isValid() || !m_cookieJar)
+ return false;
+ int lastRow = row + count - 1;
+ beginRemoveRows(parent, row, lastRow);
+ QList<QNetworkCookie> lst = m_cookieJar->allCookies();
+ for (int i = lastRow; i >= row; --i)
+ {
+ lst.removeAt(i);
+ }
+ m_cookieJar->setAllCookies(lst);
+ endRemoveRows();
+ return true;
+}
+
+
+void CookieModel::cookiesChanged()
+{
+ reset();
+}
+
+
+
+// ------------------------------------------------------------------------------------------------
+
+
+CookiesDialog::CookiesDialog(CookieJar *cookieJar, QWidget *parent)
+ : QDialog(parent)
+{
+ setupUi(this);
+ setWindowFlags(Qt::Sheet);
+ CookieModel *model = new CookieModel(cookieJar, this);
+ m_proxyModel = new QSortFilterProxyModel(this);
+ connect(search, SIGNAL(textChanged(QString)),
+ m_proxyModel, SLOT(setFilterFixedString(QString)));
+ connect(removeButton, SIGNAL(clicked()), cookiesTable, SLOT(removeOne()));
+ connect(removeAllButton, SIGNAL(clicked()), cookiesTable, SLOT(removeAll()));
+ m_proxyModel->setSourceModel(model);
+ cookiesTable->verticalHeader()->hide();
+ cookiesTable->setSelectionBehavior(QAbstractItemView::SelectRows);
+ cookiesTable->setModel(m_proxyModel);
+ cookiesTable->setAlternatingRowColors(true);
+ cookiesTable->setTextElideMode(Qt::ElideMiddle);
+ cookiesTable->setShowGrid(false);
+ cookiesTable->setSortingEnabled(true);
+ QFont f = font();
+ f.setPointSize(10);
+ QFontMetrics fm(f);
+ int height = fm.height() + fm.height() / 3;
+ cookiesTable->verticalHeader()->setDefaultSectionSize(height);
+ cookiesTable->verticalHeader()->setMinimumSectionSize(-1);
+ for (int i = 0; i < model->columnCount(); ++i)
+ {
+ int header = cookiesTable->horizontalHeader()->sectionSizeHint(i);
+ switch (i)
+ {
+ case 0:
+ header = fm.width(QLatin1String("averagehost.domain.com"));
+ break;
+ case 1:
+ header = fm.width(QLatin1String("_session_id"));
+ break;
+ case 4:
+ header = fm.width(QDateTime::currentDateTime().toString(Qt::LocalDate));
+ break;
+ }
+ int buffer = fm.width(QLatin1String("xx"));
+ header += buffer;
+ cookiesTable->horizontalHeader()->resizeSection(i, header);
+ }
+ cookiesTable->horizontalHeader()->setStretchLastSection(true);
+}
+
+
+// ---------------------------------------------------------------------------------------------------
+
+
+CookieExceptionsModel::CookieExceptionsModel(CookieJar *cookiejar, QObject *parent)
+ : QAbstractTableModel(parent)
+ , m_cookieJar(cookiejar)
+{
+ m_allowedCookies = m_cookieJar->allowedCookies();
+ m_blockedCookies = m_cookieJar->blockedCookies();
+ m_sessionCookies = m_cookieJar->allowForSessionCookies();
+}
+
+
+QVariant CookieExceptionsModel::headerData(int section, Qt::Orientation orientation, int role) const
+{
+ if (role == Qt::SizeHintRole)
+ {
+ QFont font;
+ font.setPointSize(10);
+ QFontMetrics fm(font);
+ int height = fm.height() + fm.height() / 3;
+ int width = fm.width(headerData(section, orientation, Qt::DisplayRole).toString());
+ return QSize(width, height);
+ }
+
+ if (orientation == Qt::Horizontal
+ && role == Qt::DisplayRole)
+ {
+ switch (section)
+ {
+ case 0:
+ return i18n("Website");
+ case 1:
+ return i18n("Status");
+ }
+ }
+ return QAbstractTableModel::headerData(section, orientation, role);
+}
+
+
+QVariant CookieExceptionsModel::data(const QModelIndex &index, int role) const
+{
+ if (index.row() < 0 || index.row() >= rowCount())
+ return QVariant();
+
+ switch (role)
+ {
+ case Qt::DisplayRole:
+ case Qt::EditRole:
+ {
+ int row = index.row();
+ if (row < m_allowedCookies.count())
+ {
+ switch (index.column())
+ {
+ case 0:
+ return m_allowedCookies.at(row);
+ case 1:
+ return i18n("Allow");
+ }
+ }
+ row = row - m_allowedCookies.count();
+ if (row < m_blockedCookies.count())
+ {
+ switch (index.column())
+ {
+ case 0:
+ return m_blockedCookies.at(row);
+ case 1:
+ return i18n("Block");
+ }
+ }
+ row = row - m_blockedCookies.count();
+ if (row < m_sessionCookies.count())
+ {
+ switch (index.column())
+ {
+ case 0:
+ return m_sessionCookies.at(row);
+ case 1:
+ return i18n("Allow For Session");
+ }
+ }
+ }
+ case Qt::FontRole:
+ {
+ QFont font;
+ font.setPointSize(10);
+ return font;
+ }
+ }
+ return QVariant();
+}
+
+
+int CookieExceptionsModel::columnCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : 2;
+}
+
+
+int CookieExceptionsModel::rowCount(const QModelIndex &parent) const
+{
+ return (parent.isValid() || !m_cookieJar) ? 0 : m_allowedCookies.count() + m_blockedCookies.count() + m_sessionCookies.count();
+}
+
+
+bool CookieExceptionsModel::removeRows(int row, int count, const QModelIndex &parent)
+{
+ if (parent.isValid() || !m_cookieJar)
+ return false;
+
+ int lastRow = row + count - 1;
+ beginRemoveRows(parent, row, lastRow);
+ for (int i = lastRow; i >= row; --i)
+ {
+ if (i < m_allowedCookies.count())
+ {
+ m_allowedCookies.removeAt(row);
+ continue;
+ }
+ i = i - m_allowedCookies.count();
+ if (i < m_blockedCookies.count())
+ {
+ m_blockedCookies.removeAt(row);
+ continue;
+ }
+ i = i - m_blockedCookies.count();
+ if (i < m_sessionCookies.count())
+ {
+ m_sessionCookies.removeAt(row);
+ continue;
+ }
+ }
+ m_cookieJar->setAllowedCookies(m_allowedCookies);
+ m_cookieJar->setBlockedCookies(m_blockedCookies);
+ m_cookieJar->setAllowForSessionCookies(m_sessionCookies);
+ endRemoveRows();
+ return true;
+}
+
+
+// ----------------------------------------------------------------------------------------------------------------
+
+
+CookiesExceptionsDialog::CookiesExceptionsDialog(CookieJar *cookieJar, QWidget *parent)
+ : QDialog(parent)
+ , m_cookieJar(cookieJar)
+{
+ setupUi(this);
+ setWindowFlags(Qt::Sheet);
+ connect(removeButton, SIGNAL(clicked()), exceptionTable, SLOT(removeOne()));
+ connect(removeAllButton, SIGNAL(clicked()), exceptionTable, SLOT(removeAll()));
+ exceptionTable->verticalHeader()->hide();
+ exceptionTable->setSelectionBehavior(QAbstractItemView::SelectRows);
+ exceptionTable->setAlternatingRowColors(true);
+ exceptionTable->setTextElideMode(Qt::ElideMiddle);
+ exceptionTable->setShowGrid(false);
+ exceptionTable->setSortingEnabled(true);
+ m_exceptionsModel = new CookieExceptionsModel(cookieJar, this);
+ m_proxyModel = new QSortFilterProxyModel(this);
+ m_proxyModel->setSourceModel(m_exceptionsModel);
+ connect(search, SIGNAL(textChanged(QString)),
+ m_proxyModel, SLOT(setFilterFixedString(QString)));
+ exceptionTable->setModel(m_proxyModel);
+
+ CookieModel *cookieModel = new CookieModel(cookieJar, this);
+ domainLineEdit->setCompleter(new QCompleter(cookieModel, domainLineEdit));
+
+ connect(domainLineEdit, SIGNAL(textChanged(const QString &)),
+ this, SLOT(textChanged(const QString &)));
+ connect(blockButton, SIGNAL(clicked()), this, SLOT(block()));
+ connect(allowButton, SIGNAL(clicked()), this, SLOT(allow()));
+ connect(allowForSessionButton, SIGNAL(clicked()), this, SLOT(allowForSession()));
+
+ QFont f = font();
+ f.setPointSize(10);
+ QFontMetrics fm(f);
+ int height = fm.height() + fm.height() / 3;
+ exceptionTable->verticalHeader()->setDefaultSectionSize(height);
+ exceptionTable->verticalHeader()->setMinimumSectionSize(-1);
+ for (int i = 0; i < m_exceptionsModel->columnCount(); ++i)
+ {
+ int header = exceptionTable->horizontalHeader()->sectionSizeHint(i);
+ switch (i)
+ {
+ case 0:
+ header = fm.width(QLatin1String("averagebiglonghost.domain.com"));
+ break;
+ case 1:
+ header = fm.width(QLatin1String("Allow For Session"));
+ break;
+ }
+ int buffer = fm.width(QLatin1String("xx"));
+ header += buffer;
+ exceptionTable->horizontalHeader()->resizeSection(i, header);
+ }
+}
+
+
+void CookiesExceptionsDialog::textChanged(const QString &text)
+{
+ bool enabled = !text.isEmpty();
+ blockButton->setEnabled(enabled);
+ allowButton->setEnabled(enabled);
+ allowForSessionButton->setEnabled(enabled);
+}
+
+
+void CookiesExceptionsDialog::block()
+{
+ if (domainLineEdit->text().isEmpty())
+ return;
+ m_exceptionsModel->m_blockedCookies.append(domainLineEdit->text());
+ m_cookieJar->setBlockedCookies(m_exceptionsModel->m_blockedCookies);
+ m_exceptionsModel->reset();
+}
+
+
+void CookiesExceptionsDialog::allow()
+{
+ if (domainLineEdit->text().isEmpty())
+ return;
+ m_exceptionsModel->m_allowedCookies.append(domainLineEdit->text());
+ m_cookieJar->setAllowedCookies(m_exceptionsModel->m_allowedCookies);
+ m_exceptionsModel->reset();
+}
+
+
+void CookiesExceptionsDialog::allowForSession()
+{
+ if (domainLineEdit->text().isEmpty())
+ return;
+ m_exceptionsModel->m_sessionCookies.append(domainLineEdit->text());
+ m_cookieJar->setAllowForSessionCookies(m_exceptionsModel->m_sessionCookies);
+ m_exceptionsModel->reset();
+}
diff --git a/src/cookiejar.h b/src/cookiejar.h
new file mode 100644
index 00000000..27071b6d
--- /dev/null
+++ b/src/cookiejar.h
@@ -0,0 +1,200 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef COOKIEJAR_H
+#define COOKIEJAR_H
+
+
+// KDE Includes
+#include <QDialog>
+
+// Qt Includes
+#include <QNetworkCookieJar>
+#include <QAbstractItemModel>
+#include <QStringList>
+#include <QTableView>
+
+// Forward Declarations
+class QSortFilterProxyModel;
+class QKeyEvent;
+class AutoSaver;
+
+
+class CookieJar : public QNetworkCookieJar
+{
+ friend class CookieModel;
+ Q_OBJECT
+ Q_PROPERTY(AcceptPolicy acceptPolicy READ acceptPolicy WRITE setAcceptPolicy)
+ Q_PROPERTY(KeepPolicy keepPolicy READ keepPolicy WRITE setKeepPolicy)
+ Q_PROPERTY(QStringList blockedCookies READ blockedCookies WRITE setBlockedCookies)
+ Q_PROPERTY(QStringList allowedCookies READ allowedCookies WRITE setAllowedCookies)
+ Q_PROPERTY(QStringList allowForSessionCookies READ allowForSessionCookies WRITE setAllowForSessionCookies)
+ Q_ENUMS(KeepPolicy)
+ Q_ENUMS(AcceptPolicy)
+
+signals:
+ void cookiesChanged();
+
+public:
+ enum AcceptPolicy
+ {
+ AcceptAlways,
+ AcceptNever,
+ AcceptOnlyFromSitesNavigatedTo
+ };
+
+ enum KeepPolicy
+ {
+ KeepUntilExpire,
+ KeepUntilExit,
+ KeepUntilTimeLimit
+ };
+
+ CookieJar(QObject *parent = 0);
+ ~CookieJar();
+
+ QList<QNetworkCookie> cookiesForUrl(const QUrl &url) const;
+ bool setCookiesFromUrl(const QList<QNetworkCookie> &cookieList, const QUrl &url);
+
+ AcceptPolicy acceptPolicy() const;
+ void setAcceptPolicy(AcceptPolicy policy);
+
+ KeepPolicy keepPolicy() const;
+ void setKeepPolicy(KeepPolicy policy);
+
+ QStringList blockedCookies() const;
+ QStringList allowedCookies() const;
+ QStringList allowForSessionCookies() const;
+
+ void setBlockedCookies(const QStringList &list);
+ void setAllowedCookies(const QStringList &list);
+ void setAllowForSessionCookies(const QStringList &list);
+
+public slots:
+ void clear();
+ void loadSettings();
+
+private slots:
+ void save();
+
+private:
+ void purgeOldCookies();
+ void load();
+ bool m_loaded;
+ AutoSaver *m_saveTimer;
+
+ AcceptPolicy m_acceptCookies;
+ KeepPolicy m_keepCookies;
+
+ QStringList m_exceptions_block;
+ QStringList m_exceptions_allow;
+ QStringList m_exceptions_allowForSession;
+};
+
+
+// -------------------------------------------------------------------------------------------------------------
+
+
+class CookieModel : public QAbstractTableModel
+{
+ Q_OBJECT
+
+public:
+ CookieModel(CookieJar *jar, QObject *parent = 0);
+ QVariant headerData(int section, Qt::Orientation orientation, int role) const;
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+ int columnCount(const QModelIndex &parent = QModelIndex()) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
+
+private slots:
+ void cookiesChanged();
+
+private:
+ CookieJar *m_cookieJar;
+};
+
+
+// ----------------------------------------------------------------------------------------------------------------------
+
+
+#include "ui_cookies.h"
+
+class CookiesDialog : public QDialog, public Ui_CookiesDialog
+{
+ Q_OBJECT
+
+public:
+ CookiesDialog(CookieJar *cookieJar, QWidget *parent = 0);
+
+private:
+ QSortFilterProxyModel *m_proxyModel;
+};
+
+class CookieExceptionsModel : public QAbstractTableModel
+{
+ Q_OBJECT
+ friend class CookiesExceptionsDialog;
+
+public:
+ CookieExceptionsModel(CookieJar *cookieJar, QObject *parent = 0);
+ QVariant headerData(int section, Qt::Orientation orientation, int role) const;
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+ int columnCount(const QModelIndex &parent = QModelIndex()) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
+
+private:
+ CookieJar *m_cookieJar;
+
+ // Domains we allow, Domains we block, Domains we allow for this session
+ QStringList m_allowedCookies;
+ QStringList m_blockedCookies;
+ QStringList m_sessionCookies;
+};
+
+
+// -----------------------------------------------------------------------------------------------------------------
+
+
+#include "ui_cookiesexceptions.h"
+
+class CookiesExceptionsDialog : public QDialog, public Ui_CookiesExceptionsDialog
+{
+ Q_OBJECT
+
+public:
+ CookiesExceptionsDialog(CookieJar *cookieJar, QWidget *parent = 0);
+
+private slots:
+ void block();
+ void allow();
+ void allowForSession();
+ void textChanged(const QString &text);
+
+private:
+ CookieExceptionsModel *m_exceptionsModel;
+ QSortFilterProxyModel *m_proxyModel;
+ CookieJar *m_cookieJar;
+};
+
+#endif // COOKIEJAR_H
diff --git a/src/cookies.ui b/src/cookies.ui
new file mode 100644
index 00000000..49ad3a96
--- /dev/null
+++ b/src/cookies.ui
@@ -0,0 +1,107 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>CookiesDialog</class>
+ <widget class="QDialog" name="CookiesDialog">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>550</width>
+ <height>370</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Cookies</string>
+ </property>
+ <layout class="QGridLayout">
+ <item row="0" column="0">
+ <spacer>
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>252</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item row="0" column="1">
+ <widget class="KLineEdit" name="search"/>
+ </item>
+ <item row="1" column="0" colspan="2">
+ <widget class="EditTableView" name="cookiesTable"/>
+ </item>
+ <item row="2" column="0" colspan="2">
+ <layout class="QHBoxLayout">
+ <item>
+ <widget class="QPushButton" name="removeButton">
+ <property name="text">
+ <string>&amp;Remove</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QPushButton" name="removeAllButton">
+ <property name="text">
+ <string>Remove &amp;All Cookies</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <spacer>
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item>
+ <widget class="QDialogButtonBox" name="buttonBox">
+ <property name="standardButtons">
+ <set>QDialogButtonBox::Ok</set>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>KLineEdit</class>
+ <extends>QLineEdit</extends>
+ <header>klineedit.h</header>
+ </customwidget>
+ <customwidget>
+ <class>EditTableView</class>
+ <extends>QTableView</extends>
+ <header>edittableview.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>accepted()</signal>
+ <receiver>CookiesDialog</receiver>
+ <slot>accept()</slot>
+ <hints>
+ <hint type="sourcelabel">
+ <x>472</x>
+ <y>329</y>
+ </hint>
+ <hint type="destinationlabel">
+ <x>461</x>
+ <y>356</y>
+ </hint>
+ </hints>
+ </connection>
+ </connections>
+</ui>
diff --git a/src/cookiesexceptions.ui b/src/cookiesexceptions.ui
new file mode 100644
index 00000000..de59eee0
--- /dev/null
+++ b/src/cookiesexceptions.ui
@@ -0,0 +1,179 @@
+<ui version="4.0" >
+ <class>CookiesExceptionsDialog</class>
+ <widget class="QDialog" name="CookiesExceptionsDialog" >
+ <property name="geometry" >
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>466</width>
+ <height>446</height>
+ </rect>
+ </property>
+ <property name="windowTitle" >
+ <string>Cookie Exceptions</string>
+ </property>
+ <layout class="QVBoxLayout" >
+ <item>
+ <widget class="QGroupBox" name="newExceptionGroupBox" >
+ <property name="title" >
+ <string>New Exception</string>
+ </property>
+ <layout class="QGridLayout" >
+ <item row="0" column="0" >
+ <layout class="QHBoxLayout" >
+ <item>
+ <widget class="QLabel" name="label" >
+ <property name="text" >
+ <string>Domain:</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="KLineEdit" name="domainLineEdit" />
+ </item>
+ </layout>
+ </item>
+ <item row="1" column="0" >
+ <layout class="QHBoxLayout" >
+ <item>
+ <spacer>
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>81</width>
+ <height>25</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item>
+ <widget class="QPushButton" name="blockButton" >
+ <property name="enabled" >
+ <bool>false</bool>
+ </property>
+ <property name="text" >
+ <string>Block</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QPushButton" name="allowForSessionButton" >
+ <property name="enabled" >
+ <bool>false</bool>
+ </property>
+ <property name="text" >
+ <string>Allow For Session</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QPushButton" name="allowButton" >
+ <property name="enabled" >
+ <bool>false</bool>
+ </property>
+ <property name="text" >
+ <string>Allow</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QGroupBox" name="ExceptionsGroupBox" >
+ <property name="title" >
+ <string>Exceptions</string>
+ </property>
+ <layout class="QGridLayout" >
+ <item row="0" column="0" colspan="3" >
+ <spacer>
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>252</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item row="0" column="3" >
+ <widget class="KLineEdit" name="search" />
+ </item>
+ <item row="1" column="0" colspan="4" >
+ <widget class="EditTableView" name="exceptionTable" />
+ </item>
+ <item row="2" column="0" >
+ <widget class="QPushButton" name="removeButton" >
+ <property name="text" >
+ <string>&amp;Remove</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1" >
+ <widget class="QPushButton" name="removeAllButton" >
+ <property name="text" >
+ <string>Remove &amp;All</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="2" colspan="2" >
+ <spacer>
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QDialogButtonBox" name="buttonBox" >
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="standardButtons" >
+ <set>QDialogButtonBox::Ok</set>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>EditTableView</class>
+ <extends>QTableView</extends>
+ <header>edittableview.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>accepted()</signal>
+ <receiver>CookiesExceptionsDialog</receiver>
+ <slot>accept()</slot>
+ <hints>
+ <hint type="sourcelabel" >
+ <x>381</x>
+ <y>428</y>
+ </hint>
+ <hint type="destinationlabel" >
+ <x>336</x>
+ <y>443</y>
+ </hint>
+ </hints>
+ </connection>
+ </connections>
+</ui>
diff --git a/src/download.cpp b/src/download.cpp
new file mode 100644
index 00000000..9489b270
--- /dev/null
+++ b/src/download.cpp
@@ -0,0 +1,224 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007 Lukas Appelhans <l.appelhans@gmx.de>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// local Includes
+#include "download.h"
+#include "download.moc"
+
+// KDE Includes
+#include <KDebug>
+#include <KFileDialog>
+#include <KGlobalSettings>
+#include <KMessageBox>
+#include <KMimeType>
+#include <KStandardDirs>
+
+// Qt Includes
+#include <QFile>
+#include <QFileInfo>
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+
+
+DownloadManager::DownloadManager()
+ : QObject()
+{
+}
+
+
+DownloadManager::~DownloadManager()
+{
+ foreach(Download *download, m_downloads)
+ {
+ // cancel all unfinished downloads
+ download->cancel();
+ delete download;
+ }
+}
+
+
+void DownloadManager::newDownload(const KUrl &srcUrl, const KUrl &destUrl)
+{
+ KUrl destination = destUrl;
+ Download::DownloadType type;
+
+ KSharedPtr<KMimeType> mimeType = KMimeType::findByPath(srcUrl.prettyUrl());
+
+ QString typeText = KMimeType::extractKnownExtension(srcUrl.fileName());
+ typeText += " (" + mimeType->name() + ")";
+
+ int answer = KMessageBox::questionYesNoCancel(NULL,
+ i18n("Download '%1'?\n""Type: %2", srcUrl.prettyUrl(), typeText),
+ i18n("Download '%1'...", srcUrl.fileName()),
+ KStandardGuiItem::save(),
+ KStandardGuiItem::open(),
+ KStandardGuiItem::cancel(),
+ "showOpenSaveDownloadDialog"
+ );
+
+ switch (answer)
+ {
+ case KMessageBox::Cancel:
+ return;
+ break;
+
+ case KMessageBox::Yes: // ----- SAVE
+ // if destination is empty than ask for download path (if showOpenSaveDownloadDialog setting enabled)
+ if (destination.isEmpty())
+ {
+ destination = downloadDestination(srcUrl.fileName());
+ }
+ type = Download::Save;
+ break;
+
+ case KMessageBox::No: // ----- OPEN
+ // Download file to tmp dir
+ destination.setDirectory(KStandardDirs::locateLocal("tmp", "", true));
+ destination.addPath(srcUrl.fileName());
+ type = Download::Open;
+ break;
+
+ default:
+ // impossible
+ break;
+ };
+
+ // if user canceled download than abort
+ if (destination.isEmpty())
+ return;
+
+ Download *download = new Download(srcUrl, destination, type);
+ connect(download, SIGNAL(downloadFinished(int)), this, SLOT(slotDownloadFinished(int)));
+ m_downloads.append(download);
+}
+
+
+const QList<Download *> &DownloadManager::downloads() const
+{
+ return m_downloads;
+};
+
+
+KUrl DownloadManager::downloadDestination(const QString &filename)
+{
+ KUrl destination = ReKonfig::downloadDir();
+ if (destination.isEmpty())
+ destination = KGlobalSettings::downloadPath();
+ destination.addPath(filename);
+
+ if (!ReKonfig::downloadToDefaultDir())
+ {
+ destination = KFileDialog::getSaveUrl(destination);
+ // if user canceled the download return empty url
+ if (destination.isEmpty())
+ return KUrl();
+ }
+ return destination;
+}
+
+
+void DownloadManager::slotDownloadFinished(int errorCode)
+{
+ Q_UNUSED(errorCode)
+
+ // if sender exists and list contains it - (open and) delete it
+ Download *download = qobject_cast<Download *>(sender());
+ if (download && m_downloads.contains(download))
+ {
+ if (download->type() == Download::Open)
+ {
+ KSharedPtr<KMimeType> mimeType = KMimeType::findByPath(download->destUrl().prettyUrl());
+ KRun::runUrl(download->destUrl(), mimeType->name(), NULL, true);
+ }
+ disconnect(download, SIGNAL(downloadFinished(int)), this, SLOT(slotDownloadFinished(int)));
+ int index = m_downloads.indexOf(download);
+ delete m_downloads.takeAt(index);
+ return;
+ }
+ kWarning() << "Could not find download or invalid sender. Sender:" << sender();
+}
+
+
+//----
+
+#include <KJob>
+#include <KIO/Job>
+#include <KIO/CopyJob>
+
+
+Download::Download(const KUrl &srcUrl, const KUrl &destUrl, DownloadType type)
+ : QObject()
+ , m_srcUrl(srcUrl)
+ , m_destUrl(destUrl)
+ , m_type(type)
+{
+ Q_ASSERT(!m_srcUrl.isEmpty());
+ Q_ASSERT(!m_destUrl.isEmpty());
+ kDebug() << "DownloadFile: " << m_srcUrl.url() << " to dest: " << m_destUrl.url();
+
+ m_copyJob = KIO::file_copy(m_srcUrl, m_destUrl);
+ connect(m_copyJob, SIGNAL(result(KJob *)), SLOT(slotResult(KJob *)));
+}
+
+
+Download::~Download()
+{
+}
+
+
+void Download::cancel()
+{
+ bool result = m_copyJob->kill(KJob::EmitResult);
+ Q_ASSERT(result);
+}
+
+
+void Download::slotResult(KJob *job)
+{
+ switch (job->error())
+ {
+ case 0: //The download has finished
+ {
+ kDebug() << "Downloading successfully finished: " << m_destUrl.url();
+ break;
+ }
+ case KIO::ERR_FILE_ALREADY_EXIST:
+ {
+ kWarning() << "ERROR - File already exists";
+ break;
+ }
+ case KIO::ERR_USER_CANCELED:
+ {
+ kWarning() << "ERROR - User canceled the downlaod";
+ break;
+ }
+ default:
+ kWarning() << "We are sorry to say you, that there were errors while downloading :(";
+ break;
+ }
+
+ // inform the world
+ emit downloadFinished(job->error());
+}
diff --git a/src/download.h b/src/download.h
new file mode 100644
index 00000000..0ad01e69
--- /dev/null
+++ b/src/download.h
@@ -0,0 +1,141 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007 Lukas Appelhans <l.appelhans@gmx.de>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef DOWNLOAD_H
+#define DOWNLOAD_H
+
+// Auto Includes
+#include "rekonq.h"
+
+// KDE Includes
+#include <KIO/FileCopyJob>
+
+// Qt Includes
+#include <QObject>
+
+// Forward Declarations
+class KJob;
+
+namespace KIO
+{
+class Job;
+}
+
+
+/**
+ * This class lets rekonq to download an object from the network.
+ * Creating a new object, you can continue downloading a file also
+ * when rekonq is closed.
+ *
+ */
+class Download : public QObject
+{
+ Q_OBJECT
+
+public:
+ enum DownloadType { Save, Open };
+
+ /**
+ * Class constructor. This is the unique method we need to
+ * use this class. In fact Download class needs to know just
+ * "where" catch the file to download and where it has to put it
+ *
+ * @param srcUrl the source url
+ * @param destUrl the destination url
+ *
+ */
+ Download(const KUrl &srcUrl, const KUrl &destUrl, DownloadType type);
+
+ /**
+ * class destructor
+ */
+ ~Download();
+
+ KUrl srcUrl() const
+ {
+ return m_srcUrl;
+ }
+ KUrl destUrl() const
+ {
+ return m_destUrl;
+ }
+ DownloadType type() const
+ {
+ return m_type;
+ }
+ void cancel();
+
+signals:
+ void downloadFinished(int errorCode);
+
+private slots:
+ void slotResult(KJob *job);
+
+private:
+ KIO::FileCopyJob *m_copyJob;
+ KUrl m_srcUrl;
+ KUrl m_destUrl;
+ KUrl m_destFile;
+ QByteArray m_data;
+ DownloadType m_type;
+};
+
+
+// ----------------------
+
+
+class DownloadManager : public QObject
+{
+ Q_OBJECT
+
+public:
+ DownloadManager();
+ ~DownloadManager();
+
+ /**
+ * @short Creates new download job.
+ * This method lets you to download a file from a remote source url
+ * to a local destination url.
+ *
+ * @param srcUrl the source url
+ * @param destUrl the destination url (default value is your default download destination setting)
+ *
+ */
+ void newDownload(const KUrl &srcUrl, const KUrl &destUrl = KUrl());
+
+ const QList<Download *> &downloads() const;
+
+public slots:
+ void slotDownloadFinished(int errorCode);
+
+private:
+ KUrl downloadDestination(const QString &filename);
+
+ QList<Download *> m_downloads;
+};
+
+
+//--
+
+
+#endif
diff --git a/src/edittableview.cpp b/src/edittableview.cpp
new file mode 100644
index 00000000..bf1ef370
--- /dev/null
+++ b/src/edittableview.cpp
@@ -0,0 +1,61 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#include "edittableview.h"
+#include <QtGui/QKeyEvent>
+
+EditTableView::EditTableView(QWidget *parent)
+ : QTableView(parent)
+{
+}
+
+void EditTableView::keyPressEvent(QKeyEvent *event)
+{
+ if ((event->key() == Qt::Key_Delete
+ || event->key() == Qt::Key_Backspace)
+ && model())
+ {
+ removeOne();
+ }
+ else
+ {
+ QAbstractItemView::keyPressEvent(event);
+ }
+}
+
+void EditTableView::removeOne()
+{
+ if (!model() || !selectionModel())
+ return;
+ int row = currentIndex().row();
+ model()->removeRow(row, rootIndex());
+ QModelIndex idx = model()->index(row, 0, rootIndex());
+ if (!idx.isValid())
+ idx = model()->index(row - 1, 0, rootIndex());
+ selectionModel()->select(idx, QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
+}
+
+void EditTableView::removeAll()
+{
+ if (model())
+ model()->removeRows(0, model()->rowCount(rootIndex()), rootIndex());
+}
diff --git a/src/edittableview.h b/src/edittableview.h
new file mode 100644
index 00000000..dbc9a145
--- /dev/null
+++ b/src/edittableview.h
@@ -0,0 +1,42 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef EDITTABLEVIEW_H
+#define EDITTABLEVIEW_H
+
+#include <QtGui/QTableView>
+
+class EditTableView : public QTableView
+{
+ Q_OBJECT
+
+public:
+ EditTableView(QWidget *parent = 0);
+ void keyPressEvent(QKeyEvent *event);
+
+public slots:
+ void removeOne();
+ void removeAll();
+};
+
+#endif // EDITTABLEVIEW_H
+
diff --git a/src/edittreeview.cpp b/src/edittreeview.cpp
new file mode 100644
index 00000000..49730d67
--- /dev/null
+++ b/src/edittreeview.cpp
@@ -0,0 +1,61 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#include "edittreeview.h"
+
+#include <QtGui/QKeyEvent>
+
+EditTreeView::EditTreeView(QWidget *parent)
+ : QTreeView(parent)
+{
+}
+
+void EditTreeView::keyPressEvent(QKeyEvent *event)
+{
+ if ((event->key() == Qt::Key_Delete
+ || event->key() == Qt::Key_Backspace)
+ && model())
+ {
+ removeOne();
+ }
+ else
+ {
+ QAbstractItemView::keyPressEvent(event);
+ }
+}
+
+void EditTreeView::removeOne()
+{
+ if (!model())
+ return;
+ QModelIndex ci = currentIndex();
+ int row = ci.row();
+ model()->removeRow(row, ci.parent());
+}
+
+void EditTreeView::removeAll()
+{
+ if (!model())
+ return;
+ model()->removeRows(0, model()->rowCount(rootIndex()), rootIndex());
+}
+
diff --git a/src/edittreeview.h b/src/edittreeview.h
new file mode 100644
index 00000000..5be0dc45
--- /dev/null
+++ b/src/edittreeview.h
@@ -0,0 +1,41 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef EDITTREEVIEW_H
+#define EDITTREEVIEW_H
+
+#include <QtGui/QTreeView>
+
+class EditTreeView : public QTreeView
+{
+ Q_OBJECT
+
+public:
+ EditTreeView(QWidget *parent = 0);
+ void keyPressEvent(QKeyEvent *event);
+
+public slots:
+ void removeOne();
+ void removeAll();
+};
+
+#endif // EDITTREEVIEW_H
+
diff --git a/src/findbar.cpp b/src/findbar.cpp
new file mode 100644
index 00000000..11d890c1
--- /dev/null
+++ b/src/findbar.cpp
@@ -0,0 +1,137 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "findbar.h"
+#include "findbar.moc"
+
+// KDE Includes
+#include <KLineEdit>
+#include <KAction>
+#include <KIcon>
+#include <KPushButton>
+#include <klocalizedstring.h>
+
+// Qt Includes
+#include <QtGui>
+
+
+FindBar::FindBar(KXmlGuiWindow *mainwindow)
+ : QWidget(mainwindow)
+ , m_lineEdit(new KLineEdit(this))
+ , m_matchCase(new QCheckBox(i18n("&Match case"), this))
+{
+ QHBoxLayout *layout = new QHBoxLayout;
+
+ // cosmetic
+ layout->setContentsMargins(2, 0, 2, 0);
+
+ // hide button
+ QToolButton *hideButton = new QToolButton(this);
+ hideButton->setAutoRaise(true);
+ hideButton->setIcon(KIcon("dialog-close"));
+ connect(hideButton, SIGNAL(clicked()), this, SLOT(hide()));
+ layout->addWidget(hideButton);
+ layout->setAlignment(hideButton, Qt::AlignLeft | Qt::AlignTop);
+
+ // label
+ QLabel *label = new QLabel(i18n("Find: "));
+ layout->addWidget(label);
+
+ // lineEdit, focusProxy
+ setFocusProxy(m_lineEdit);
+ m_lineEdit->setMaximumWidth(250);
+ connect(m_lineEdit, SIGNAL(textChanged(const QString &)), mainwindow, SLOT(slotFind(const QString &)));
+ layout->addWidget(m_lineEdit);
+
+ // buttons
+ KPushButton *findNext = new KPushButton(KIcon("go-down"), i18n("&Next"), this);
+ KPushButton *findPrev = new KPushButton(KIcon("go-up"), i18n("&Previous"), this);
+ connect(findNext, SIGNAL(clicked()), mainwindow, SLOT(slotFindNext()));
+ connect(findPrev, SIGNAL(clicked()), mainwindow, SLOT(slotFindPrevious()));
+ layout->addWidget(findNext);
+ layout->addWidget(findPrev);
+
+ // Case sensitivity. Deliberately set so this is off by default.
+ m_matchCase->setCheckState(Qt::Unchecked);
+ m_matchCase->setTristate(false);
+ layout->addWidget(m_matchCase);
+
+ // stretching widget on the left
+ layout->addStretch();
+
+ setLayout(layout);
+
+ // we start off hidden
+ hide();
+}
+
+
+FindBar::~FindBar()
+{
+}
+
+
+KLineEdit *FindBar::lineEdit() const
+{
+ return m_lineEdit;
+}
+
+
+bool FindBar::matchCase() const
+{
+ return m_matchCase->isChecked();
+}
+
+
+void FindBar::clear()
+{
+ m_lineEdit->setText(QString());
+}
+
+
+void FindBar::showFindBar()
+{
+ // show findbar if not visible
+ if (!isVisible())
+ {
+ show();
+ }
+ // set focus to findbar if user select showFindBar shortcut
+ m_lineEdit->setFocus();
+ m_lineEdit->selectAll();
+}
+
+
+void FindBar::keyPressEvent(QKeyEvent* event)
+{
+ if (event->key() == Qt::Key_Escape)
+ {
+ hide();
+ return;
+ }
+ if (event->key() == Qt::Key_Return && !m_lineEdit->text().isEmpty())
+ {
+ emit searchString(m_lineEdit->text());
+ return;
+ }
+ QWidget::keyPressEvent(event);
+}
+
diff --git a/src/findbar.h b/src/findbar.h
new file mode 100644
index 00000000..15a82e1e
--- /dev/null
+++ b/src/findbar.h
@@ -0,0 +1,61 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef FINDBAR_H
+#define FINDBAR_H
+
+// KDE Includes
+#include <KLineEdit>
+#include <KToolBar>
+#include <KXmlGuiWindow>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+
+
+class FindBar : public QWidget
+{
+ Q_OBJECT
+
+public:
+ FindBar(KXmlGuiWindow *mainwindow);
+ ~FindBar();
+ KLineEdit *lineEdit() const;
+ bool matchCase() const;
+
+public slots:
+ void clear();
+ void showFindBar();
+
+protected Q_SLOTS:
+ void keyPressEvent(QKeyEvent* event);
+
+signals:
+ void searchString(const QString &);
+
+private:
+ KLineEdit *m_lineEdit;
+ QCheckBox *m_matchCase;
+};
+
+
+#endif
diff --git a/src/history.cpp b/src/history.cpp
new file mode 100644
index 00000000..afcb477a
--- /dev/null
+++ b/src/history.cpp
@@ -0,0 +1,1459 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008 Benjamin C. Meyer <ben@meyerhome.net>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "history.h"
+#include "history.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "autosaver.h"
+#include "application.h"
+
+// KDE Includes
+#include <KDebug>
+#include <KStandardDirs>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+#include <QtWebKit>
+
+#include <QtAlgorithms>
+
+
+static const unsigned int HISTORY_VERSION = 23;
+
+
+HistoryManager::HistoryManager(QObject *parent)
+ : QWebHistoryInterface(parent)
+ , m_saveTimer(new AutoSaver(this))
+ , m_historyLimit(30)
+ , m_historyModel(0)
+ , m_historyFilterModel(0)
+ , m_historyTreeModel(0)
+{
+ m_expiredTimer.setSingleShot(true);
+ connect(&m_expiredTimer, SIGNAL(timeout()), this, SLOT(checkForExpired()));
+ connect(this, SIGNAL(entryAdded(const HistoryItem &)), m_saveTimer, SLOT(changeOccurred()));
+ connect(this, SIGNAL(entryRemoved(const HistoryItem &)), m_saveTimer, SLOT(changeOccurred()));
+ load();
+
+ m_historyModel = new HistoryModel(this, this);
+ m_historyFilterModel = new HistoryFilterModel(m_historyModel, this);
+ m_historyTreeModel = new HistoryTreeModel(m_historyFilterModel, this);
+
+ // QWebHistoryInterface will delete the history manager
+ QWebHistoryInterface::setDefaultInterface(this);
+}
+
+
+HistoryManager::~HistoryManager()
+{
+ m_saveTimer->saveIfNeccessary();
+}
+
+
+QList<HistoryItem> HistoryManager::history() const
+{
+ return m_history;
+}
+
+
+bool HistoryManager::historyContains(const QString &url) const
+{
+ return m_historyFilterModel->historyContains(url);
+}
+
+
+void HistoryManager::addHistoryEntry(const QString &url)
+{
+ QUrl cleanUrl(url);
+ cleanUrl.setPassword(QString());
+ cleanUrl.setHost(cleanUrl.host().toLower());
+ HistoryItem item(cleanUrl.toString(), QDateTime::currentDateTime());
+ addHistoryEntry(item);
+}
+
+
+void HistoryManager::setHistory(const QList<HistoryItem> &history, bool loadedAndSorted)
+{
+ m_history = history;
+
+ // verify that it is sorted by date
+ if (!loadedAndSorted)
+ qSort(m_history.begin(), m_history.end());
+
+ checkForExpired();
+
+ if (loadedAndSorted)
+ {
+ m_lastSavedUrl = m_history.value(0).url;
+ }
+ else
+ {
+ m_lastSavedUrl = QString();
+ m_saveTimer->changeOccurred();
+ }
+ emit historyReset();
+}
+
+
+HistoryModel *HistoryManager::historyModel() const
+{
+ return m_historyModel;
+}
+
+
+HistoryFilterModel *HistoryManager::historyFilterModel() const
+{
+ return m_historyFilterModel;
+}
+
+
+HistoryTreeModel *HistoryManager::historyTreeModel() const
+{
+ return m_historyTreeModel;
+}
+
+
+void HistoryManager::checkForExpired()
+{
+ if (m_historyLimit < 0 || m_history.isEmpty())
+ return;
+
+ QDateTime now = QDateTime::currentDateTime();
+ int nextTimeout = 0;
+
+ while (!m_history.isEmpty())
+ {
+ QDateTime checkForExpired = m_history.last().dateTime;
+ checkForExpired.setDate(checkForExpired.date().addDays(m_historyLimit));
+ if (now.daysTo(checkForExpired) > 7)
+ {
+ // check at most in a week to prevent int overflows on the timer
+ nextTimeout = 7 * 86400;
+ }
+ else
+ {
+ nextTimeout = now.secsTo(checkForExpired);
+ }
+ if (nextTimeout > 0)
+ break;
+ HistoryItem item = m_history.takeLast();
+ // remove from saved file also
+ m_lastSavedUrl = QString();
+ emit entryRemoved(item);
+ }
+
+ if (nextTimeout > 0)
+ m_expiredTimer.start(nextTimeout * 1000);
+}
+
+
+void HistoryManager::addHistoryEntry(const HistoryItem &item)
+{
+ QWebSettings *globalSettings = QWebSettings::globalSettings();
+ if (globalSettings->testAttribute(QWebSettings::PrivateBrowsingEnabled))
+ return;
+
+ m_history.prepend(item);
+ emit entryAdded(item);
+ if (m_history.count() == 1)
+ checkForExpired();
+}
+
+
+void HistoryManager::updateHistoryEntry(const KUrl &url, const QString &title)
+{
+ for (int i = 0; i < m_history.count(); ++i)
+ {
+ if (url == m_history.at(i).url)
+ {
+ m_history[i].title = title;
+ m_saveTimer->changeOccurred();
+ if (m_lastSavedUrl.isEmpty())
+ m_lastSavedUrl = m_history.at(i).url;
+ emit entryUpdated(i);
+ break;
+ }
+ }
+}
+
+
+void HistoryManager::removeHistoryEntry(const HistoryItem &item)
+{
+ m_lastSavedUrl.clear();
+ m_history.removeOne(item);
+ emit entryRemoved(item);
+}
+
+
+void HistoryManager::removeHistoryEntry(const KUrl &url, const QString &title)
+{
+ for (int i = 0; i < m_history.count(); ++i)
+ {
+ if (url == m_history.at(i).url
+ && (title.isEmpty() || title == m_history.at(i).title))
+ {
+ removeHistoryEntry(m_history.at(i));
+ break;
+ }
+ }
+}
+
+
+int HistoryManager::historyLimit() const
+{
+ return m_historyLimit;
+}
+
+
+void HistoryManager::setHistoryLimit(int limit)
+{
+ if (m_historyLimit == limit)
+ return;
+ m_historyLimit = limit;
+ checkForExpired();
+ m_saveTimer->changeOccurred();
+}
+
+
+void HistoryManager::clear()
+{
+ m_history.clear();
+ m_lastSavedUrl = QString();
+ m_saveTimer->changeOccurred();
+ m_saveTimer->saveIfNeccessary();
+ historyReset();
+}
+
+
+void HistoryManager::loadSettings()
+{
+ int historyExpire = ReKonfig::expireHistory();
+ int days;
+ switch (historyExpire)
+ {
+ case 0: days = 1; break;
+ case 1: days = 7; break;
+ case 2: days = 14; break;
+ case 3: days = 30; break;
+ case 4: days = 365; break;
+ case 5: days = -1; break;
+ default: days = -1;
+ }
+ m_historyLimit = days;
+}
+
+
+void HistoryManager::load()
+{
+ loadSettings();
+
+ QString historyFilePath = KStandardDirs::locateLocal("appdata" , "history");
+ QFile historyFile(historyFilePath);
+ if (!historyFile.exists())
+ return;
+ if (!historyFile.open(QFile::ReadOnly))
+ {
+ kWarning() << "Unable to open history file" << historyFile.fileName();
+ return;
+ }
+
+ QList<HistoryItem> list;
+ QDataStream in(&historyFile);
+ // Double check that the history file is sorted as it is read in
+ bool needToSort = false;
+ HistoryItem lastInsertedItem;
+ QByteArray data;
+ QDataStream stream;
+ QBuffer buffer;
+ stream.setDevice(&buffer);
+ while (!historyFile.atEnd())
+ {
+ in >> data;
+ buffer.close();
+ buffer.setBuffer(&data);
+ buffer.open(QIODevice::ReadOnly);
+ quint32 ver;
+ stream >> ver;
+ if (ver != HISTORY_VERSION)
+ continue;
+ HistoryItem item;
+ stream >> item.url;
+ stream >> item.dateTime;
+ stream >> item.title;
+
+ if (!item.dateTime.isValid())
+ continue;
+
+ if (item == lastInsertedItem)
+ {
+ if (lastInsertedItem.title.isEmpty() && !list.isEmpty())
+ list[0].title = item.title;
+ continue;
+ }
+
+ if (!needToSort && !list.isEmpty() && lastInsertedItem < item)
+ needToSort = true;
+
+ list.prepend(item);
+ lastInsertedItem = item;
+ }
+ if (needToSort)
+ qSort(list.begin(), list.end());
+
+ setHistory(list, true);
+
+ // If we had to sort re-write the whole history sorted
+ if (needToSort)
+ {
+ m_lastSavedUrl = QString();
+ m_saveTimer->changeOccurred();
+ }
+}
+
+
+void HistoryManager::save()
+{
+ bool saveAll = m_lastSavedUrl.isEmpty();
+ int first = m_history.count() - 1;
+ if (!saveAll)
+ {
+ // find the first one to save
+ for (int i = 0; i < m_history.count(); ++i)
+ {
+ if (m_history.at(i).url == m_lastSavedUrl)
+ {
+ first = i - 1;
+ break;
+ }
+ }
+ }
+ if (first == m_history.count() - 1)
+ saveAll = true;
+
+ QString historyFilePath = KStandardDirs::locateLocal("appdata" , "history");
+ QFile historyFile(historyFilePath);
+
+ // When saving everything use a temporary file to prevent possible data loss.
+ QTemporaryFile tempFile;
+ tempFile.setAutoRemove(false);
+ bool open = false;
+ if (saveAll)
+ {
+ open = tempFile.open();
+ }
+ else
+ {
+ open = historyFile.open(QFile::Append);
+ }
+
+ if (!open)
+ {
+ kWarning() << "Unable to open history file for saving"
+ << (saveAll ? tempFile.fileName() : historyFile.fileName());
+ return;
+ }
+
+ QDataStream out(saveAll ? &tempFile : &historyFile);
+ for (int i = first; i >= 0; --i)
+ {
+ QByteArray data;
+ QDataStream stream(&data, QIODevice::WriteOnly);
+ HistoryItem item = m_history.at(i);
+ stream << HISTORY_VERSION << item.url << item.dateTime << item.title;
+ out << data;
+ }
+ tempFile.close();
+
+ if (saveAll)
+ {
+ if (historyFile.exists() && !historyFile.remove())
+ kWarning() << "History: error removing old history." << historyFile.errorString();
+ if (!tempFile.rename(historyFile.fileName()))
+ kWarning() << "History: error moving new history over old." << tempFile.errorString() << historyFile.fileName();
+ }
+ m_lastSavedUrl = m_history.value(0).url;
+}
+
+
+// --------------------------------------------------------------------------------------------------------------------------
+
+
+HistoryModel::HistoryModel(HistoryManager *history, QObject *parent)
+ : QAbstractTableModel(parent)
+ , m_history(history)
+{
+ Q_ASSERT(m_history);
+ connect(m_history, SIGNAL(historyReset()), this, SLOT(historyReset()));
+ connect(m_history, SIGNAL(entryRemoved(const HistoryItem &)), this, SLOT(historyReset()));
+ connect(m_history, SIGNAL(entryAdded(const HistoryItem &)), this, SLOT(entryAdded()));
+ connect(m_history, SIGNAL(entryUpdated(int)), this, SLOT(entryUpdated(int)));
+}
+
+
+void HistoryModel::historyReset()
+{
+ reset();
+}
+
+
+void HistoryModel::entryAdded()
+{
+ beginInsertRows(QModelIndex(), 0, 0);
+ endInsertRows();
+}
+
+
+void HistoryModel::entryUpdated(int offset)
+{
+ QModelIndex idx = index(offset, 0);
+ emit dataChanged(idx, idx);
+}
+
+
+QVariant HistoryModel::headerData(int section, Qt::Orientation orientation, int role) const
+{
+ if (orientation == Qt::Horizontal
+ && role == Qt::DisplayRole)
+ {
+ switch (section)
+ {
+ case 0: return i18n("Title");
+ case 1: return i18n("Address");
+ }
+ }
+ return QAbstractTableModel::headerData(section, orientation, role);
+}
+
+
+QVariant HistoryModel::data(const QModelIndex &index, int role) const
+{
+ QList<HistoryItem> lst = m_history->history();
+ if (index.row() < 0 || index.row() >= lst.size())
+ return QVariant();
+
+ const HistoryItem &item = lst.at(index.row());
+ switch (role)
+ {
+ case DateTimeRole:
+ return item.dateTime;
+ case DateRole:
+ return item.dateTime.date();
+ case UrlRole:
+ return QUrl(item.url);
+ case UrlStringRole:
+ return item.url;
+ case Qt::DisplayRole:
+ case Qt::EditRole:
+ {
+ switch (index.column())
+ {
+ case 0:
+ // when there is no title try to generate one from the url
+ if (item.title.isEmpty())
+ {
+ QString page = QFileInfo(QUrl(item.url).path()).fileName();
+ if (!page.isEmpty())
+ return page;
+ return item.url;
+ }
+ return item.title;
+ case 1:
+ return item.url;
+ }
+ }
+ case Qt::DecorationRole:
+ if (index.column() == 0)
+ {
+ return Application::instance()->icon(item.url);
+ }
+ }
+ return QVariant();
+}
+
+
+int HistoryModel::columnCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : 2;
+}
+
+
+int HistoryModel::rowCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : m_history->history().count();
+}
+
+
+bool HistoryModel::removeRows(int row, int count, const QModelIndex &parent)
+{
+ if (parent.isValid())
+ return false;
+ int lastRow = row + count - 1;
+ beginRemoveRows(parent, row, lastRow);
+ QList<HistoryItem> lst = m_history->history();
+ for (int i = lastRow; i >= row; --i)
+ lst.removeAt(i);
+ disconnect(m_history, SIGNAL(historyReset()), this, SLOT(historyReset()));
+ m_history->setHistory(lst);
+ connect(m_history, SIGNAL(historyReset()), this, SLOT(historyReset()));
+ endRemoveRows();
+ return true;
+}
+
+
+
+// -----------------------------------------------------------------------------------------------
+
+
+#define MOVEDROWS 10
+
+
+/*
+ Maps the first bunch of items of the source model to the root
+*/
+HistoryMenuModel::HistoryMenuModel(HistoryTreeModel *sourceModel, QObject *parent)
+ : QAbstractProxyModel(parent)
+ , m_treeModel(sourceModel)
+{
+ setSourceModel(sourceModel);
+}
+
+
+int HistoryMenuModel::bumpedRows() const
+{
+ QModelIndex first = m_treeModel->index(0, 0);
+ if (!first.isValid())
+ return 0;
+ return qMin(m_treeModel->rowCount(first), MOVEDROWS);
+}
+
+
+int HistoryMenuModel::columnCount(const QModelIndex &parent) const
+{
+ return m_treeModel->columnCount(mapToSource(parent));
+}
+
+
+int HistoryMenuModel::rowCount(const QModelIndex &parent) const
+{
+ if (parent.column() > 0)
+ return 0;
+
+ if (!parent.isValid())
+ {
+ int folders = sourceModel()->rowCount();
+ int bumpedItems = bumpedRows();
+ if (bumpedItems <= MOVEDROWS
+ && bumpedItems == sourceModel()->rowCount(sourceModel()->index(0, 0)))
+ --folders;
+ return bumpedItems + folders;
+ }
+
+ if (parent.internalId() == -1)
+ {
+ if (parent.row() < bumpedRows())
+ return 0;
+ }
+
+ QModelIndex idx = mapToSource(parent);
+ int defaultCount = sourceModel()->rowCount(idx);
+ if (idx == sourceModel()->index(0, 0))
+ return defaultCount - bumpedRows();
+ return defaultCount;
+}
+
+
+QModelIndex HistoryMenuModel::mapFromSource(const QModelIndex &sourceIndex) const
+{
+ // currently not used or autotested
+ Q_ASSERT(false);
+ int sr = m_treeModel->mapToSource(sourceIndex).row();
+ return createIndex(sourceIndex.row(), sourceIndex.column(), sr);
+}
+
+
+QModelIndex HistoryMenuModel::mapToSource(const QModelIndex &proxyIndex) const
+{
+ if (!proxyIndex.isValid())
+ return QModelIndex();
+
+ if (proxyIndex.internalId() == -1)
+ {
+ int bumpedItems = bumpedRows();
+ if (proxyIndex.row() < bumpedItems)
+ return m_treeModel->index(proxyIndex.row(), proxyIndex.column(), m_treeModel->index(0, 0));
+ if (bumpedItems <= MOVEDROWS && bumpedItems == sourceModel()->rowCount(m_treeModel->index(0, 0)))
+ --bumpedItems;
+ return m_treeModel->index(proxyIndex.row() - bumpedItems, proxyIndex.column());
+ }
+
+ QModelIndex historyIndex = m_treeModel->sourceModel()->index(proxyIndex.internalId(), proxyIndex.column());
+ QModelIndex treeIndex = m_treeModel->mapFromSource(historyIndex);
+ return treeIndex;
+}
+
+
+QModelIndex HistoryMenuModel::index(int row, int column, const QModelIndex &parent) const
+{
+ if (row < 0
+ || column < 0 || column >= columnCount(parent)
+ || parent.column() > 0)
+ return QModelIndex();
+ if (!parent.isValid())
+ return createIndex(row, column, -1);
+
+ QModelIndex treeIndexParent = mapToSource(parent);
+
+ int bumpedItems = 0;
+ if (treeIndexParent == m_treeModel->index(0, 0))
+ bumpedItems = bumpedRows();
+ QModelIndex treeIndex = m_treeModel->index(row + bumpedItems, column, treeIndexParent);
+ QModelIndex historyIndex = m_treeModel->mapToSource(treeIndex);
+ int historyRow = historyIndex.row();
+ if (historyRow == -1)
+ historyRow = treeIndex.row();
+ return createIndex(row, column, historyRow);
+}
+
+
+QModelIndex HistoryMenuModel::parent(const QModelIndex &index) const
+{
+ int offset = index.internalId();
+ if (offset == -1 || !index.isValid())
+ return QModelIndex();
+
+ QModelIndex historyIndex = m_treeModel->sourceModel()->index(index.internalId(), 0);
+ QModelIndex treeIndex = m_treeModel->mapFromSource(historyIndex);
+ QModelIndex treeIndexParent = treeIndex.parent();
+
+ int sr = m_treeModel->mapToSource(treeIndexParent).row();
+ int bumpedItems = bumpedRows();
+ if (bumpedItems <= MOVEDROWS && bumpedItems == sourceModel()->rowCount(sourceModel()->index(0, 0)))
+ --bumpedItems;
+ return createIndex(bumpedItems + treeIndexParent.row(), treeIndexParent.column(), sr);
+}
+
+
+// -------------------------------------------------------------------------------------------------------------
+
+
+HistoryMenu::HistoryMenu(QWidget *parent)
+ : ModelMenu(parent)
+ , m_history(0)
+{
+ connect(this, SIGNAL(activated(const QModelIndex &)), this, SLOT(activated(const QModelIndex &)));
+ setHoverRole(HistoryModel::UrlStringRole);
+}
+
+
+void HistoryMenu::activated(const QModelIndex &index)
+{
+ emit openUrl(index.data(HistoryModel::UrlRole).toUrl());
+}
+
+
+bool HistoryMenu::prePopulated()
+{
+ if (!m_history)
+ {
+ m_history = Application::historyManager();
+ m_historyMenuModel = new HistoryMenuModel(m_history->historyTreeModel(), this);
+ setModel(m_historyMenuModel);
+ }
+ // initial actions
+ for (int i = 0; i < m_initialActions.count(); ++i)
+ addAction(m_initialActions.at(i));
+ if (!m_initialActions.isEmpty())
+ addSeparator();
+ setFirstSeparator(m_historyMenuModel->bumpedRows());
+
+ return false;
+}
+
+
+void HistoryMenu::postPopulated()
+{
+ if (m_history->history().count() > 0)
+ addSeparator();
+
+ KAction *showAllAction = new KAction(i18n("Show All History"), this);
+ connect(showAllAction, SIGNAL(triggered()), this, SLOT(showHistoryDialog()));
+ addAction(showAllAction);
+
+ KAction *clearAction = new KAction(i18n("Clear History"), this);
+ connect(clearAction, SIGNAL(triggered()), m_history, SLOT(clear()));
+ addAction(clearAction);
+}
+
+
+void HistoryMenu::showHistoryDialog()
+{
+ HistoryDialog *dialog = new HistoryDialog(this);
+ connect(dialog, SIGNAL(openUrl(const KUrl&)), this, SIGNAL(openUrl(const KUrl&)));
+ dialog->show();
+}
+
+
+void HistoryMenu::setInitialActions(QList<QAction*> actions)
+{
+ m_initialActions = actions;
+ for (int i = 0; i < m_initialActions.count(); ++i)
+ addAction(m_initialActions.at(i));
+}
+
+
+// --------------------------------------------------------------------------------------------------------------
+
+
+TreeProxyModel::TreeProxyModel(QObject *parent) : QSortFilterProxyModel(parent)
+{
+ setSortRole(HistoryModel::DateTimeRole);
+ setFilterCaseSensitivity(Qt::CaseInsensitive);
+}
+
+
+bool TreeProxyModel::filterAcceptsRow(int source_row, const QModelIndex &source_parent) const
+{
+ if (!source_parent.isValid())
+ return true;
+ return QSortFilterProxyModel::filterAcceptsRow(source_row, source_parent);
+}
+
+
+// -----------------------------------------------------------------------------------------------------
+
+
+HistoryDialog::HistoryDialog(QWidget *parent, HistoryManager *setHistory) : QDialog(parent)
+{
+ HistoryManager *history = setHistory;
+ if (!history)
+ history = Application::historyManager();
+ setupUi(this);
+ tree->setUniformRowHeights(true);
+ tree->setSelectionBehavior(QAbstractItemView::SelectRows);
+ tree->setTextElideMode(Qt::ElideMiddle);
+ QAbstractItemModel *model = history->historyTreeModel();
+ TreeProxyModel *proxyModel = new TreeProxyModel(this);
+ connect(search, SIGNAL(textChanged(QString)),
+ proxyModel, SLOT(setFilterFixedString(QString)));
+ connect(removeButton, SIGNAL(clicked()), tree, SLOT(removeOne()));
+ connect(removeAllButton, SIGNAL(clicked()), history, SLOT(clear()));
+ proxyModel->setSourceModel(model);
+ tree->setModel(proxyModel);
+ tree->setExpanded(proxyModel->index(0, 0), true);
+ tree->setAlternatingRowColors(true);
+ QFontMetrics fm(font());
+ int header = fm.width(QLatin1Char('m')) * 40;
+ tree->header()->resizeSection(0, header);
+ tree->header()->setStretchLastSection(true);
+ connect(tree, SIGNAL(activated(const QModelIndex&)),
+ this, SLOT(open()));
+ tree->setContextMenuPolicy(Qt::CustomContextMenu);
+ connect(tree, SIGNAL(customContextMenuRequested(const QPoint &)),
+ this, SLOT(customContextMenuRequested(const QPoint &)));
+}
+
+
+void HistoryDialog::customContextMenuRequested(const QPoint &pos)
+{
+ QMenu menu;
+ QModelIndex index = tree->indexAt(pos);
+ index = index.sibling(index.row(), 0);
+ if (index.isValid() && !tree->model()->hasChildren(index))
+ {
+ menu.addAction(i18n("Open"), this, SLOT(open()));
+ menu.addSeparator();
+ menu.addAction(i18n("Copy"), this, SLOT(copy()));
+ }
+ menu.addAction(i18n("Delete"), tree, SLOT(removeOne()));
+ menu.exec(QCursor::pos());
+}
+
+
+void HistoryDialog::open()
+{
+ QModelIndex index = tree->currentIndex();
+ if (!index.parent().isValid())
+ return;
+ emit openUrl(index.data(HistoryModel::UrlRole).toUrl());
+}
+
+
+void HistoryDialog::copy()
+{
+ QModelIndex index = tree->currentIndex();
+ if (!index.parent().isValid())
+ return;
+ QString url = index.data(HistoryModel::UrlStringRole).toString();
+
+ QClipboard *clipboard = QApplication::clipboard();
+ clipboard->setText(url);
+}
+
+
+// ---------------------------------------------------------------------------------------------------------------
+
+HistoryFilterModel::HistoryFilterModel(QAbstractItemModel *sourceModel, QObject *parent)
+ : QAbstractProxyModel(parent),
+ m_loaded(false)
+{
+ setSourceModel(sourceModel);
+}
+
+
+int HistoryFilterModel::historyLocation(const QString &url) const
+{
+ load();
+ if (!m_historyHash.contains(url))
+ return 0;
+ return sourceModel()->rowCount() - m_historyHash.value(url);
+}
+
+
+QVariant HistoryFilterModel::data(const QModelIndex &index, int role) const
+{
+ return QAbstractProxyModel::data(index, role);
+}
+
+
+void HistoryFilterModel::setSourceModel(QAbstractItemModel *newSourceModel)
+{
+ if (sourceModel())
+ {
+ disconnect(sourceModel(), SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ disconnect(sourceModel(), SIGNAL(dataChanged(const QModelIndex &, const QModelIndex &)),
+ this, SLOT(dataChanged(const QModelIndex &, const QModelIndex &)));
+ disconnect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsInserted(const QModelIndex &, int, int)));
+ disconnect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ }
+
+ QAbstractProxyModel::setSourceModel(newSourceModel);
+
+ if (sourceModel())
+ {
+ m_loaded = false;
+ connect(sourceModel(), SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ connect(sourceModel(), SIGNAL(dataChanged(const QModelIndex &, const QModelIndex &)),
+ this, SLOT(sourceDataChanged(const QModelIndex &, const QModelIndex &)));
+ connect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsInserted(const QModelIndex &, int, int)));
+ connect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ }
+}
+
+
+void HistoryFilterModel::sourceDataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight)
+{
+ emit dataChanged(mapFromSource(topLeft), mapFromSource(bottomRight));
+}
+
+
+QVariant HistoryFilterModel::headerData(int section, Qt::Orientation orientation, int role) const
+{
+ return sourceModel()->headerData(section, orientation, role);
+}
+
+
+void HistoryFilterModel::sourceReset()
+{
+ m_loaded = false;
+ reset();
+}
+
+
+int HistoryFilterModel::rowCount(const QModelIndex &parent) const
+{
+ load();
+ if (parent.isValid())
+ return 0;
+ return m_historyHash.count();
+}
+
+
+int HistoryFilterModel::columnCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : 2;
+}
+
+
+QModelIndex HistoryFilterModel::mapToSource(const QModelIndex &proxyIndex) const
+{
+ load();
+ int sourceRow = sourceModel()->rowCount() - proxyIndex.internalId();
+ return sourceModel()->index(sourceRow, proxyIndex.column());
+}
+
+
+QModelIndex HistoryFilterModel::mapFromSource(const QModelIndex &sourceIndex) const
+{
+ load();
+ QString url = sourceIndex.data(HistoryModel::UrlStringRole).toString();
+ if (!m_historyHash.contains(url))
+ return QModelIndex();
+
+ // This can be done in a binary search, but we can't use qBinary find
+ // because it can't take: qBinaryFind(m_sourceRow.end(), m_sourceRow.begin(), v);
+ // so if this is a performance bottlneck then convert to binary search, until then
+ // the cleaner/easier to read code wins the day.
+ int realRow = -1;
+ int sourceModelRow = sourceModel()->rowCount() - sourceIndex.row();
+
+ for (int i = 0; i < m_sourceRow.count(); ++i)
+ {
+ if (m_sourceRow.at(i) == sourceModelRow)
+ {
+ realRow = i;
+ break;
+ }
+ }
+ if (realRow == -1)
+ return QModelIndex();
+
+ return createIndex(realRow, sourceIndex.column(), sourceModel()->rowCount() - sourceIndex.row());
+}
+
+
+QModelIndex HistoryFilterModel::index(int row, int column, const QModelIndex &parent) const
+{
+ load();
+ if (row < 0 || row >= rowCount(parent)
+ || column < 0 || column >= columnCount(parent))
+ return QModelIndex();
+
+ return createIndex(row, column, m_sourceRow[row]);
+}
+
+
+QModelIndex HistoryFilterModel::parent(const QModelIndex &) const
+{
+ return QModelIndex();
+}
+
+
+void HistoryFilterModel::load() const
+{
+ if (m_loaded)
+ return;
+ m_sourceRow.clear();
+ m_historyHash.clear();
+ m_historyHash.reserve(sourceModel()->rowCount());
+ for (int i = 0; i < sourceModel()->rowCount(); ++i)
+ {
+ QModelIndex idx = sourceModel()->index(i, 0);
+ QString url = idx.data(HistoryModel::UrlStringRole).toString();
+ if (!m_historyHash.contains(url))
+ {
+ m_sourceRow.append(sourceModel()->rowCount() - i);
+ m_historyHash[url] = sourceModel()->rowCount() - i;
+ }
+ }
+ m_loaded = true;
+}
+
+
+void HistoryFilterModel::sourceRowsInserted(const QModelIndex &parent, int start, int end)
+{
+ Q_ASSERT(start == end && start == 0);
+ Q_UNUSED(end);
+ if (!m_loaded)
+ return;
+ QModelIndex idx = sourceModel()->index(start, 0, parent);
+ QString url = idx.data(HistoryModel::UrlStringRole).toString();
+ if (m_historyHash.contains(url))
+ {
+ int sourceRow = sourceModel()->rowCount() - m_historyHash[url];
+ int realRow = mapFromSource(sourceModel()->index(sourceRow, 0)).row();
+ beginRemoveRows(QModelIndex(), realRow, realRow);
+ m_sourceRow.removeAt(realRow);
+ m_historyHash.remove(url);
+ endRemoveRows();
+ }
+ beginInsertRows(QModelIndex(), 0, 0);
+ m_historyHash.insert(url, sourceModel()->rowCount() - start);
+ m_sourceRow.insert(0, sourceModel()->rowCount());
+ endInsertRows();
+}
+
+
+void HistoryFilterModel::sourceRowsRemoved(const QModelIndex &, int start, int end)
+{
+ Q_UNUSED(start);
+ Q_UNUSED(end);
+ sourceReset();
+}
+
+
+/*
+ Removing a continuous block of rows will remove filtered rows too as this is
+ the users intention.
+*/
+bool HistoryFilterModel::removeRows(int row, int count, const QModelIndex &parent)
+{
+ if (row < 0 || count <= 0 || row + count > rowCount(parent) || parent.isValid())
+ return false;
+ int lastRow = row + count - 1;
+ disconnect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ beginRemoveRows(parent, row, lastRow);
+ int oldCount = rowCount();
+ int start = sourceModel()->rowCount() - m_sourceRow.value(row);
+ int end = sourceModel()->rowCount() - m_sourceRow.value(lastRow);
+ sourceModel()->removeRows(start, end - start + 1);
+ endRemoveRows();
+ connect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ m_loaded = false;
+ if (oldCount - count != rowCount())
+ reset();
+ return true;
+}
+
+
+// ------------------------------------------------------------------------------------------------------
+
+
+HistoryCompletionModel::HistoryCompletionModel(QObject *parent)
+ : QAbstractProxyModel(parent)
+{
+}
+
+
+QVariant HistoryCompletionModel::data(const QModelIndex &index, int role) const
+{
+ if (sourceModel()
+ && (role == Qt::EditRole || role == Qt::DisplayRole)
+ && index.isValid())
+ {
+ QModelIndex idx = mapToSource(index);
+ idx = idx.sibling(idx.row(), 1);
+ QString urlString = idx.data(HistoryModel::UrlStringRole).toString();
+ if (index.row() % 2)
+ {
+ QUrl url = urlString;
+ QString s = url.toString(QUrl::RemoveScheme
+ | QUrl::RemoveUserInfo
+ | QUrl::StripTrailingSlash);
+ return s.mid(2); // strip // from the front
+ }
+ return urlString;
+ }
+ return QAbstractProxyModel::data(index, role);
+}
+
+
+int HistoryCompletionModel::rowCount(const QModelIndex &parent) const
+{
+ return (parent.isValid() || !sourceModel()) ? 0 : sourceModel()->rowCount(parent) * 2;
+}
+
+
+int HistoryCompletionModel::columnCount(const QModelIndex &parent) const
+{
+ return (parent.isValid()) ? 0 : 1;
+}
+
+
+QModelIndex HistoryCompletionModel::mapFromSource(const QModelIndex &sourceIndex) const
+{
+ int row = sourceIndex.row() * 2;
+ return index(row, sourceIndex.column());
+}
+
+
+QModelIndex HistoryCompletionModel::mapToSource(const QModelIndex &proxyIndex) const
+{
+ if (!sourceModel())
+ return QModelIndex();
+ int row = proxyIndex.row() / 2;
+ return sourceModel()->index(row, proxyIndex.column());
+}
+
+
+QModelIndex HistoryCompletionModel::index(int row, int column, const QModelIndex &parent) const
+{
+ if (row < 0 || row >= rowCount(parent)
+ || column < 0 || column >= columnCount(parent))
+ return QModelIndex();
+ return createIndex(row, column, 0);
+}
+
+
+QModelIndex HistoryCompletionModel::parent(const QModelIndex &) const
+{
+ return QModelIndex();
+}
+
+
+void HistoryCompletionModel::setSourceModel(QAbstractItemModel *newSourceModel)
+{
+ if (sourceModel())
+ {
+ disconnect(sourceModel(), SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ disconnect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceReset()));
+ disconnect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceReset()));
+ }
+
+ QAbstractProxyModel::setSourceModel(newSourceModel);
+
+ if (newSourceModel)
+ {
+ connect(newSourceModel, SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ connect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceReset()));
+ connect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceReset()));
+ }
+
+ reset();
+}
+
+
+void HistoryCompletionModel::sourceReset()
+{
+ reset();
+}
+
+
+// ------------------------------------------------------------------------------------------------------
+
+
+HistoryTreeModel::HistoryTreeModel(QAbstractItemModel *sourceModel, QObject *parent)
+ : QAbstractProxyModel(parent)
+{
+ setSourceModel(sourceModel);
+}
+
+
+QVariant HistoryTreeModel::headerData(int section, Qt::Orientation orientation, int role) const
+{
+ return sourceModel()->headerData(section, orientation, role);
+}
+
+
+QVariant HistoryTreeModel::data(const QModelIndex &index, int role) const
+{
+ if ((role == Qt::EditRole || role == Qt::DisplayRole))
+ {
+ int start = index.internalId();
+ if (start == 0)
+ {
+ int offset = sourceDateRow(index.row());
+ if (index.column() == 0)
+ {
+ QModelIndex idx = sourceModel()->index(offset, 0);
+ QDate date = idx.data(HistoryModel::DateRole).toDate();
+ if (date == QDate::currentDate())
+ return i18n("Earlier Today");
+ return date.toString(QLatin1String("dddd, MMMM d, yyyy"));
+ }
+ if (index.column() == 1)
+ {
+ return i18np("1 item", "%1 items", rowCount(index.sibling(index.row(), 0)));
+ }
+ }
+ }
+ if (role == Qt::DecorationRole && index.column() == 0 && !index.parent().isValid())
+ return KIcon("view-history");
+ if (role == HistoryModel::DateRole && index.column() == 0 && index.internalId() == 0)
+ {
+ int offset = sourceDateRow(index.row());
+ QModelIndex idx = sourceModel()->index(offset, 0);
+ return idx.data(HistoryModel::DateRole);
+ }
+
+ return QAbstractProxyModel::data(index, role);
+}
+
+
+int HistoryTreeModel::columnCount(const QModelIndex &parent) const
+{
+ return sourceModel()->columnCount(mapToSource(parent));
+}
+
+
+int HistoryTreeModel::rowCount(const QModelIndex &parent) const
+{
+ if (parent.internalId() != 0
+ || parent.column() > 0
+ || !sourceModel())
+ return 0;
+
+ // row count OF dates
+ if (!parent.isValid())
+ {
+ if (!m_sourceRowCache.isEmpty())
+ return m_sourceRowCache.count();
+ QDate currentDate;
+ int rows = 0;
+ int totalRows = sourceModel()->rowCount();
+
+ for (int i = 0; i < totalRows; ++i)
+ {
+ QDate rowDate = sourceModel()->index(i, 0).data(HistoryModel::DateRole).toDate();
+ if (rowDate != currentDate)
+ {
+ m_sourceRowCache.append(i);
+ currentDate = rowDate;
+ ++rows;
+ }
+ }
+ Q_ASSERT(m_sourceRowCache.count() == rows);
+ return rows;
+ }
+
+ // row count FOR a date
+ int start = sourceDateRow(parent.row());
+ int end = sourceDateRow(parent.row() + 1);
+ return (end - start);
+}
+
+
+// Translate the top level date row into the offset where that date starts
+int HistoryTreeModel::sourceDateRow(int row) const
+{
+ if (row <= 0)
+ return 0;
+
+ if (m_sourceRowCache.isEmpty())
+ rowCount(QModelIndex());
+
+ if (row >= m_sourceRowCache.count())
+ {
+ if (!sourceModel())
+ return 0;
+ return sourceModel()->rowCount();
+ }
+ return m_sourceRowCache.at(row);
+}
+
+
+QModelIndex HistoryTreeModel::mapToSource(const QModelIndex &proxyIndex) const
+{
+ int offset = proxyIndex.internalId();
+ if (offset == 0)
+ return QModelIndex();
+ int startDateRow = sourceDateRow(offset - 1);
+ return sourceModel()->index(startDateRow + proxyIndex.row(), proxyIndex.column());
+}
+
+
+QModelIndex HistoryTreeModel::index(int row, int column, const QModelIndex &parent) const
+{
+ if (row < 0
+ || column < 0 || column >= columnCount(parent)
+ || parent.column() > 0)
+ return QModelIndex();
+
+ if (!parent.isValid())
+ return createIndex(row, column, 0);
+ return createIndex(row, column, parent.row() + 1);
+}
+
+
+QModelIndex HistoryTreeModel::parent(const QModelIndex &index) const
+{
+ int offset = index.internalId();
+ if (offset == 0 || !index.isValid())
+ return QModelIndex();
+ return createIndex(offset - 1, 0, 0);
+}
+
+
+bool HistoryTreeModel::hasChildren(const QModelIndex &parent) const
+{
+ QModelIndex grandparent = parent.parent();
+ if (!grandparent.isValid())
+ return true;
+ return false;
+}
+
+
+Qt::ItemFlags HistoryTreeModel::flags(const QModelIndex &index) const
+{
+ if (!index.isValid())
+ return Qt::NoItemFlags;
+ return Qt::ItemIsSelectable | Qt::ItemIsEnabled | Qt::ItemIsDragEnabled;
+}
+
+
+bool HistoryTreeModel::removeRows(int row, int count, const QModelIndex &parent)
+{
+ if (row < 0 || count <= 0 || row + count > rowCount(parent))
+ return false;
+
+ if (parent.isValid())
+ {
+ // removing pages
+ int offset = sourceDateRow(parent.row());
+ return sourceModel()->removeRows(offset + row, count);
+ }
+ else
+ {
+ // removing whole dates
+ for (int i = row + count - 1; i >= row; --i)
+ {
+ QModelIndex dateParent = index(i, 0);
+ int offset = sourceDateRow(dateParent.row());
+ if (!sourceModel()->removeRows(offset, rowCount(dateParent)))
+ return false;
+ }
+ }
+ return true;
+}
+
+
+void HistoryTreeModel::setSourceModel(QAbstractItemModel *newSourceModel)
+{
+ if (sourceModel())
+ {
+ disconnect(sourceModel(), SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ disconnect(sourceModel(), SIGNAL(layoutChanged()), this, SLOT(sourceReset()));
+ disconnect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsInserted(const QModelIndex &, int, int)));
+ disconnect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ }
+
+ QAbstractProxyModel::setSourceModel(newSourceModel);
+
+ if (newSourceModel)
+ {
+ connect(sourceModel(), SIGNAL(modelReset()), this, SLOT(sourceReset()));
+ connect(sourceModel(), SIGNAL(layoutChanged()), this, SLOT(sourceReset()));
+ connect(sourceModel(), SIGNAL(rowsInserted(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsInserted(const QModelIndex &, int, int)));
+ connect(sourceModel(), SIGNAL(rowsRemoved(const QModelIndex &, int, int)),
+ this, SLOT(sourceRowsRemoved(const QModelIndex &, int, int)));
+ }
+
+ reset();
+}
+
+
+void HistoryTreeModel::sourceReset()
+{
+ m_sourceRowCache.clear();
+ reset();
+}
+
+
+void HistoryTreeModel::sourceRowsInserted(const QModelIndex &parent, int start, int end)
+{
+ Q_UNUSED(parent); // Avoid warnings when compiling release
+ Q_ASSERT(!parent.isValid());
+ if (start != 0 || start != end)
+ {
+ m_sourceRowCache.clear();
+ reset();
+ return;
+ }
+
+ m_sourceRowCache.clear();
+ QModelIndex treeIndex = mapFromSource(sourceModel()->index(start, 0));
+ QModelIndex treeParent = treeIndex.parent();
+ if (rowCount(treeParent) == 1)
+ {
+ beginInsertRows(QModelIndex(), 0, 0);
+ endInsertRows();
+ }
+ else
+ {
+ beginInsertRows(treeParent, treeIndex.row(), treeIndex.row());
+ endInsertRows();
+ }
+}
+
+
+QModelIndex HistoryTreeModel::mapFromSource(const QModelIndex &sourceIndex) const
+{
+ if (!sourceIndex.isValid())
+ return QModelIndex();
+
+ if (m_sourceRowCache.isEmpty())
+ rowCount(QModelIndex());
+
+ QList<int>::iterator it;
+ it = qLowerBound(m_sourceRowCache.begin(), m_sourceRowCache.end(), sourceIndex.row());
+ if (*it != sourceIndex.row())
+ --it;
+
+ int dateRow = qMax(0, it - m_sourceRowCache.begin());
+ // FIXME fix crach on history submenu open. BUG:'ASSERT failure in QList<T>::at: "index out of range"'
+ // it crashes when dateRow == 1
+ // kDebug() << m_sourceRowCache << dateRow;
+ int row = sourceIndex.row() - m_sourceRowCache.at(dateRow);
+ return createIndex(row, sourceIndex.column(), dateRow + 1);
+}
+
+
+void HistoryTreeModel::sourceRowsRemoved(const QModelIndex &parent, int start, int end)
+{
+ Q_UNUSED(parent); // Avoid warnings when compiling release
+ Q_ASSERT(!parent.isValid());
+ if (m_sourceRowCache.isEmpty())
+ return;
+ for (int i = end; i >= start;)
+ {
+ QList<int>::iterator it;
+ it = qLowerBound(m_sourceRowCache.begin(), m_sourceRowCache.end(), i);
+ // playing it safe
+ if (it == m_sourceRowCache.end())
+ {
+ m_sourceRowCache.clear();
+ reset();
+ return;
+ }
+
+ if (*it != i)
+ --it;
+ int row = qMax(0, it - m_sourceRowCache.begin());
+ int offset = m_sourceRowCache[row];
+ QModelIndex dateParent = index(row, 0);
+ // If we can remove all the rows in the date do that and skip over them
+ int rc = rowCount(dateParent);
+ if (i - rc + 1 == offset && start <= i - rc + 1)
+ {
+ beginRemoveRows(QModelIndex(), row, row);
+ m_sourceRowCache.removeAt(row);
+ i -= rc + 1;
+ }
+ else
+ {
+ beginRemoveRows(dateParent, i - offset, i - offset);
+ ++row;
+ --i;
+ }
+ for (int j = row; j < m_sourceRowCache.count(); ++j)
+ --m_sourceRowCache[j];
+ endRemoveRows();
+ }
+}
diff --git a/src/history.h b/src/history.h
new file mode 100644
index 00000000..ecae00c3
--- /dev/null
+++ b/src/history.h
@@ -0,0 +1,402 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008 Benjamin C. Meyer <ben@meyerhome.net>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef HISTORY_H
+#define HISTORY_H
+
+// Local Includes
+#include "modelmenu.h"
+
+// KDE Includes
+#include <KAction>
+#include <KUrl>
+
+// Qt Includes
+#include <QDateTime>
+#include <QHash>
+#include <QObject>
+#include <QTimer>
+#include <QSortFilterProxyModel>
+#include <QWebHistoryInterface>
+
+
+/**
+ * Elements in this class represent an history item
+ *
+ */
+
+class HistoryItem
+{
+public:
+ HistoryItem() {}
+ HistoryItem(const QString &u,
+ const QDateTime &d = QDateTime(), const QString &t = QString())
+ : title(t), url(u), dateTime(d) {}
+
+ inline bool operator==(const HistoryItem &other) const
+ {
+ return other.title == title
+ && other.url == url && other.dateTime == dateTime;
+ }
+
+ // history is sorted in reverse
+ inline bool operator <(const HistoryItem &other) const
+ {
+ return dateTime > other.dateTime;
+ }
+
+ QString title;
+ QString url;
+ QDateTime dateTime;
+};
+
+
+
+// ---------------------------------------------------------------------------------------------------------------
+
+
+class AutoSaver;
+class HistoryModel;
+class HistoryFilterModel;
+class HistoryTreeModel;
+
+
+class HistoryManager : public QWebHistoryInterface
+{
+ Q_OBJECT
+ Q_PROPERTY(int historyLimit READ historyLimit WRITE setHistoryLimit)
+
+signals:
+ void historyReset();
+ void entryAdded(const HistoryItem &item);
+ void entryRemoved(const HistoryItem &item);
+ void entryUpdated(int offset);
+
+public:
+ HistoryManager(QObject *parent = 0);
+ ~HistoryManager();
+
+ bool historyContains(const QString &url) const;
+ void addHistoryEntry(const QString &url);
+ void updateHistoryEntry(const KUrl &url, const QString &title);
+ void removeHistoryEntry(const KUrl &url, const QString &title = QString());
+
+ int historyLimit() const;
+ void setHistoryLimit(int limit);
+
+ QList<HistoryItem> history() const;
+ void setHistory(const QList<HistoryItem> &history, bool loadedAndSorted = false);
+
+ // History manager keeps around these models for use by the completer and other classes
+ HistoryModel *historyModel() const;
+ HistoryFilterModel *historyFilterModel() const;
+ HistoryTreeModel *historyTreeModel() const;
+
+public slots:
+ void clear();
+ void loadSettings();
+
+private slots:
+ void save();
+ void checkForExpired();
+
+protected:
+ void addHistoryEntry(const HistoryItem &item);
+ void removeHistoryEntry(const HistoryItem &item);
+
+private:
+ void load();
+
+ AutoSaver *m_saveTimer;
+ int m_historyLimit;
+ QTimer m_expiredTimer;
+ QList<HistoryItem> m_history;
+ QString m_lastSavedUrl;
+
+ HistoryModel *m_historyModel;
+ HistoryFilterModel *m_historyFilterModel;
+ HistoryTreeModel *m_historyTreeModel;
+};
+
+
+// --------------------------------------------------------------------------------------------------------
+
+
+class HistoryModel : public QAbstractTableModel
+{
+ Q_OBJECT
+
+public slots:
+ void historyReset();
+ void entryAdded();
+ void entryUpdated(int offset);
+
+public:
+ enum Roles
+ {
+ DateRole = Qt::UserRole + 1,
+ DateTimeRole = Qt::UserRole + 2,
+ UrlRole = Qt::UserRole + 3,
+ UrlStringRole = Qt::UserRole + 4
+ };
+
+ HistoryModel(HistoryManager *history, QObject *parent = 0);
+ QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const;
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+ int columnCount(const QModelIndex &parent = QModelIndex()) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
+
+private:
+ HistoryManager *m_history;
+};
+
+
+// ----------------------------------------------------------------------------------------------------
+
+/**
+ * Proxy model that will remove any duplicate entries.
+ * Both m_sourceRow and m_historyHash store their offsets not from
+ * the front of the list, but as offsets from the back.
+ *
+ */
+
+class HistoryFilterModel : public QAbstractProxyModel
+{
+ Q_OBJECT
+
+public:
+ HistoryFilterModel(QAbstractItemModel *sourceModel, QObject *parent = 0);
+
+ inline bool historyContains(const QString &url) const
+ {
+ load(); return m_historyHash.contains(url);
+ }
+ int historyLocation(const QString &url) const;
+
+ QModelIndex mapFromSource(const QModelIndex &sourceIndex) const;
+ QModelIndex mapToSource(const QModelIndex &proxyIndex) const;
+ void setSourceModel(QAbstractItemModel *sourceModel);
+ QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ int columnCount(const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex index(int, int, const QModelIndex& = QModelIndex()) const;
+ QModelIndex parent(const QModelIndex& index = QModelIndex()) const;
+ bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+
+private slots:
+ void sourceReset();
+ void sourceDataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight);
+ void sourceRowsInserted(const QModelIndex &parent, int start, int end);
+ void sourceRowsRemoved(const QModelIndex &, int, int);
+
+private:
+ void load() const;
+
+ mutable QList<int> m_sourceRow;
+ mutable QHash<QString, int> m_historyHash;
+ mutable bool m_loaded;
+};
+
+
+// ----------------------------------------------------------------------------------------------------------------------
+
+/**
+ * The history menu
+ * - Removes the first twenty entries and puts them as children of the top level.
+ * - If there are less then twenty entries then the first folder is also removed.
+ *
+ * The mapping is done by knowing that HistoryTreeModel is over a table
+ * We store that row offset in our index's private data.
+ *
+ */
+
+class HistoryMenuModel : public QAbstractProxyModel
+{
+ Q_OBJECT
+
+public:
+ HistoryMenuModel(HistoryTreeModel *sourceModel, QObject *parent = 0);
+ int columnCount(const QModelIndex &parent) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex mapFromSource(const QModelIndex & sourceIndex) const;
+ QModelIndex mapToSource(const QModelIndex & proxyIndex) const;
+ QModelIndex index(int, int, const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex parent(const QModelIndex &index = QModelIndex()) const;
+
+ int bumpedRows() const;
+
+private:
+ HistoryTreeModel *m_treeModel;
+};
+
+
+// ---------------------------------------------------------------------------------------------
+
+/**
+ * Menu that is dynamically populated from the history
+ *
+ */
+
+class HistoryMenu : public ModelMenu
+{
+ Q_OBJECT
+
+signals:
+ void openUrl(const KUrl &url);
+
+public:
+ HistoryMenu(QWidget *parent = 0);
+ void setInitialActions(QList<QAction*> actions);
+
+protected:
+ bool prePopulated();
+ void postPopulated();
+
+private slots:
+ void activated(const QModelIndex &index);
+ void showHistoryDialog();
+
+private:
+ HistoryManager *m_history;
+ HistoryMenuModel *m_historyMenuModel;
+ QList<QAction*> m_initialActions;
+};
+
+
+// ----------------------------------------------------------------------------------------
+
+/**
+ * Proxy model for the history model that
+ * exposes each url http://www.foo.com and
+ * it url starting at the host www.foo.com
+ *
+ */
+
+class HistoryCompletionModel : public QAbstractProxyModel
+{
+ Q_OBJECT
+
+public:
+ HistoryCompletionModel(QObject *parent = 0);
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ int columnCount(const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex mapFromSource(const QModelIndex &sourceIndex) const;
+ QModelIndex mapToSource(const QModelIndex &proxyIndex) const;
+ QModelIndex index(int, int, const QModelIndex& = QModelIndex()) const;
+ QModelIndex parent(const QModelIndex& index = QModelIndex()) const;
+ void setSourceModel(QAbstractItemModel *sourceModel);
+
+private slots:
+ void sourceReset();
+
+};
+
+
+// ---------------------------------------------------------------------------------------
+
+/**
+ * Proxy model for the history model that converts the list
+ * into a tree, one top level node per day.
+ * Used in the HistoryDialog.
+ *
+ */
+
+class HistoryTreeModel : public QAbstractProxyModel
+{
+ Q_OBJECT
+
+public:
+ HistoryTreeModel(QAbstractItemModel *sourceModel, QObject *parent = 0);
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
+ int columnCount(const QModelIndex &parent) const;
+ int rowCount(const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex mapFromSource(const QModelIndex &sourceIndex) const;
+ QModelIndex mapToSource(const QModelIndex &proxyIndex) const;
+ QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const;
+ QModelIndex parent(const QModelIndex &index = QModelIndex()) const;
+ bool hasChildren(const QModelIndex &parent = QModelIndex()) const;
+ Qt::ItemFlags flags(const QModelIndex &index) const;
+ bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
+ QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const;
+
+ void setSourceModel(QAbstractItemModel *sourceModel);
+
+private slots:
+ void sourceReset();
+ void sourceRowsInserted(const QModelIndex &parent, int start, int end);
+ void sourceRowsRemoved(const QModelIndex &parent, int start, int end);
+
+private:
+ int sourceDateRow(int row) const;
+ mutable QList<int> m_sourceRowCache;
+
+};
+
+
+// -----------------------------------------------------------------------------------------------------------------
+
+/**
+ * A modified QSortFilterProxyModel that always accepts
+ * the root nodes in the tree
+ * so filtering is only done on the children.
+ * Used in the HistoryDialog.
+ *
+ */
+
+class TreeProxyModel : public QSortFilterProxyModel
+{
+ Q_OBJECT
+
+public:
+ TreeProxyModel(QObject *parent = 0);
+
+protected:
+ bool filterAcceptsRow(int source_row, const QModelIndex &source_parent) const;
+};
+
+
+// ------------------------------------------------------------------------------------------
+
+#include "ui_history.h"
+
+class HistoryDialog : public QDialog, public Ui_HistoryDialog
+{
+ Q_OBJECT
+
+signals:
+ void openUrl(const KUrl &url);
+
+public:
+ HistoryDialog(QWidget *parent = 0, HistoryManager *history = 0);
+
+private slots:
+ void customContextMenuRequested(const QPoint &pos);
+ void open();
+ void copy();
+
+};
+
+#endif // HISTORY_H
+
diff --git a/src/history.ui b/src/history.ui
new file mode 100644
index 00000000..806bc9ad
--- /dev/null
+++ b/src/history.ui
@@ -0,0 +1,101 @@
+<ui version="4.0" >
+ <class>HistoryDialog</class>
+ <widget class="QDialog" name="HistoryDialog" >
+ <property name="geometry" >
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>758</width>
+ <height>450</height>
+ </rect>
+ </property>
+ <property name="windowTitle" >
+ <string>History</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout" >
+ <item row="0" column="0" >
+ <spacer>
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>252</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item row="0" column="1" >
+ <widget class="KLineEdit" name="search" />
+ </item>
+ <item row="1" column="0" colspan="2" >
+ <widget class="EditTreeView" name="tree" />
+ </item>
+ <item row="2" column="0" colspan="2" >
+ <layout class="QHBoxLayout" >
+ <item>
+ <widget class="QPushButton" name="removeButton" >
+ <property name="text" >
+ <string>&amp;Remove</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QPushButton" name="removeAllButton" >
+ <property name="text" >
+ <string>Remove &amp;All</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <spacer>
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item>
+ <widget class="QDialogButtonBox" name="buttonBox" >
+ <property name="standardButtons" >
+ <set>QDialogButtonBox::Ok</set>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>EditTreeView</class>
+ <extends>QTreeView</extends>
+ <header>edittreeview.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>accepted()</signal>
+ <receiver>HistoryDialog</receiver>
+ <slot>accept()</slot>
+ <hints>
+ <hint type="sourcelabel" >
+ <x>472</x>
+ <y>329</y>
+ </hint>
+ <hint type="destinationlabel" >
+ <x>461</x>
+ <y>356</y>
+ </hint>
+ </hints>
+ </connection>
+ </connections>
+</ui>
diff --git a/src/lineedit.cpp b/src/lineedit.cpp
new file mode 100644
index 00000000..c9df7bfa
--- /dev/null
+++ b/src/lineedit.cpp
@@ -0,0 +1,85 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+// Self Includes
+#include "lineedit.h"
+#include "lineedit.moc"
+
+// Qt Includes
+#include <QContextMenuEvent>
+#include <QFocusEvent>
+#include <QKeyEvent>
+
+// KDE Includes
+#include <KDebug>
+
+// Local Includes
+
+LineEdit::LineEdit(QWidget* parent)
+ : KLineEdit(parent)
+{
+ setMinimumWidth(180);
+ setFocusPolicy(Qt::WheelFocus);
+
+ setHandleSignals(true);
+}
+
+
+LineEdit::~LineEdit()
+{
+}
+
+
+void LineEdit::keyPressEvent(QKeyEvent *event)
+{
+ if (event->key() == Qt::Key_Escape)
+ {
+ clearFocus();
+ event->accept();
+ }
+
+ KLineEdit::keyPressEvent(event);
+}
+
+
+void LineEdit::contextMenuEvent(QContextMenuEvent *event)
+{
+ KLineEdit::contextMenuEvent(event);
+}
+
+
+void LineEdit::focusInEvent(QFocusEvent *event)
+{
+ selectAll();
+
+ KLineEdit::focusInEvent(event);
+}
+
+
+void LineEdit::focusOutEvent(QFocusEvent *event)
+{
+ KLineEdit::focusOutEvent(event);
+
+ // reset cursor state and deselect
+ setCursorPosition(0);
+ deselect();
+}
+
+
+
diff --git a/src/lineedit.h b/src/lineedit.h
new file mode 100644
index 00000000..f1bd8f88
--- /dev/null
+++ b/src/lineedit.h
@@ -0,0 +1,50 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef LINEEDIT_H
+#define LINEEDIT_H
+
+// Qt Includes
+
+// KDE Includes
+#include <KLineEdit>
+
+// Local Includes
+
+class QContextMenuEvent;
+class QFocusEvent;
+class QKeyEvent;
+
+class LineEdit : public KLineEdit
+{
+ Q_OBJECT
+
+public:
+ explicit LineEdit(QWidget *parent = 0);
+ virtual ~LineEdit();
+
+protected:
+ virtual void keyPressEvent(QKeyEvent*);
+ virtual void contextMenuEvent(QContextMenuEvent*);
+ virtual void focusInEvent(QFocusEvent*);
+ virtual void focusOutEvent(QFocusEvent*);
+};
+
+#endif // LINEEDIT_H
diff --git a/src/main.cpp b/src/main.cpp
new file mode 100644
index 00000000..5ada94b4
--- /dev/null
+++ b/src/main.cpp
@@ -0,0 +1,98 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#include "application.h"
+
+#include <KAboutData>
+#include <KCmdLineArgs>
+#include <KDebug>
+
+
+static const char description[] =
+ I18N_NOOP("KDE Browser Webkit Based");
+
+
+static const char version[] = "0.1alpha";
+
+
+int main(int argc, char **argv)
+{
+ KAboutData about("rekonq",
+ 0,
+ ki18n("rekonq"),
+ version,
+ ki18n(description),
+ KAboutData::License_GPL_V3,
+ ki18n("(C) 2008-2009 Andrea Diamantini"),
+ KLocalizedString(),
+ "http://rekonq.sourceforge.net",
+ "rekonq@kde.org"
+ );
+
+ // about authors
+ about.addAuthor(ki18n("Andrea Diamantini"),
+ ki18n("Project Lead, Developer, Italian translation"),
+ "adjam7@gmail.com",
+ "http://www.adjam.org");
+
+ about.addAuthor(ki18n("Domrachev Alexandr"),
+ ki18n("Developer, Russian translation"),
+ "alexandr.domrachev@gmail.com",
+ "");
+
+ about.addAuthor(ki18n("Pawel Prazak"),
+ ki18n("Developer"),
+ "kojots350@gmail.com",
+ "");
+
+ about.addAuthor(ki18n("Panagiotis Papadopoulos"),
+ ki18n("German translation"),
+ "pano_90@gmx.net",
+ "");
+
+// about.addAuthor(ki18n("your name"),
+// ki18n("your role"),
+// "your mail",
+// "your site");
+
+ // Initialize command line args
+ KCmdLineArgs::init(argc, argv, &about);
+
+ // Define the command line options using KCmdLineOptions
+ KCmdLineOptions options;
+
+ // adding URL option
+ options.add("+[URL]" , ki18n("Location to open"));
+
+ // Register the supported options
+ KCmdLineArgs::addCmdLineOptions(options);
+
+ // Add options from Application class
+ Application::addCmdLineOptions();
+
+ if (!Application::start())
+ {
+ kWarning() << "rekonq is already running!";
+ return 0;
+ }
+
+ Application app;
+ return app.exec();
+}
diff --git a/src/mainview.cpp b/src/mainview.cpp
new file mode 100644
index 00000000..d4edeb19
--- /dev/null
+++ b/src/mainview.cpp
@@ -0,0 +1,716 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Self Includes
+#include "mainview.h"
+#include "mainview.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "tabbar.h"
+#include "application.h"
+#include "mainwindow.h"
+#include "history.h"
+#include "stackedurlbar.h"
+#include "urlbar.h"
+#include "webview.h"
+
+// KDE Includes
+#include <KUrl>
+#include <KMenu>
+#include <KAction>
+#include <KShortcut>
+#include <KStandardShortcut>
+#include <KMessageBox>
+#include <KActionCollection>
+#include <KDebug>
+#include <KStandardDirs>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+#include <QtWebKit>
+
+
+
+MainView::MainView(QWidget *parent)
+ : KTabWidget(parent)
+ , m_recentlyClosedTabsAction(0)
+ , m_recentlyClosedTabsMenu(new KMenu(this))
+ , m_urlBars(new StackedUrlBar(this))
+ , m_tabBar(new TabBar(this))
+{
+ // setting tabbar
+ setTabBar(m_tabBar);
+
+ // loading pixmap path
+ m_loadingGitPath = KStandardDirs::locate("appdata" , "pics/loading.gif");
+
+ // connecting tabbar signals
+ connect(m_tabBar, SIGNAL(closeTab(int)), this, SLOT(slotCloseTab(int)));
+ connect(m_tabBar, SIGNAL(cloneTab(int)), this, SLOT(slotCloneTab(int)));
+ connect(m_tabBar, SIGNAL(closeOtherTabs(int)), this, SLOT(slotCloseOtherTabs(int)));
+ connect(m_tabBar, SIGNAL(reloadTab(int)), this, SLOT(slotReloadTab(int)));
+ connect(m_tabBar, SIGNAL(reloadAllTabs()), this, SLOT(slotReloadAllTabs()));
+ connect(m_tabBar, SIGNAL(tabMoved(int, int)), this, SLOT(moveTab(int, int)));
+
+ // current page index changing
+ connect(this, SIGNAL(currentChanged(int)), this, SLOT(slotCurrentChanged(int)));
+
+ setTabsClosable(true);
+ connect(m_tabBar, SIGNAL(tabCloseRequested(int)), this, SLOT(slotCloseTab(int)));
+
+ QTimer::singleShot(0, this, SLOT(postLaunch()));
+}
+
+
+MainView::~MainView()
+{
+}
+
+
+void MainView::postLaunch()
+{
+ // Recently Closed Tab Action
+ connect(m_recentlyClosedTabsMenu, SIGNAL(aboutToShow()), this, SLOT(aboutToShowRecentTabsMenu()));
+ connect(m_recentlyClosedTabsMenu, SIGNAL(triggered(QAction *)), this, SLOT(aboutToShowRecentTriggeredAction(QAction *)));
+ m_recentlyClosedTabsAction = new KAction(i18n("Recently Closed Tabs"), this);
+ m_recentlyClosedTabsAction->setMenu(m_recentlyClosedTabsMenu);
+ m_recentlyClosedTabsAction->setEnabled(false);
+}
+
+void MainView::showTabBar()
+{
+ if (ReKonfig::alwaysShowTabBar())
+ {
+ if (m_tabBar->isHidden())
+ {
+ m_tabBar->show();
+ }
+ return;
+ }
+
+ if (m_tabBar->count() == 1)
+ {
+ m_tabBar->hide();
+ }
+ else
+ {
+ if (m_tabBar->isHidden())
+ {
+ m_tabBar->show();
+ }
+ }
+}
+
+
+void MainView::slotWebReload()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Reload);
+ action->trigger();
+}
+
+
+void MainView::slotWebStop()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Stop);
+ action->trigger();
+}
+
+
+void MainView::slotWebBack()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Back);
+ action->trigger();
+}
+
+
+void MainView::slotWebForward()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Forward);
+ action->trigger();
+}
+
+
+void MainView::slotWebUndo()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Undo);
+ action->trigger();
+}
+
+
+void MainView::slotWebRedo()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Redo);
+ action->trigger();
+}
+
+
+void MainView::slotWebCut()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Cut);
+ action->trigger();
+}
+
+
+void MainView::slotWebCopy()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Copy);
+ action->trigger();
+}
+
+
+void MainView::slotWebPaste()
+{
+ WebView *webView = currentWebView();
+ QWebPage *currentParent = webView->webPage();
+ QAction *action = currentParent->action(QWebPage::Paste);
+ action->trigger();
+}
+
+
+void MainView::clear()
+{
+ // clear the recently closed tabs
+ m_recentlyClosedTabs.clear();
+ // clear the line edit history
+ for (int i = 0; i < m_urlBars->count(); ++i)
+ {
+ /// TODO What exacly do we need to clear here?
+ urlBar(i)->clearHistory();
+ urlBar(i)->clear();
+ }
+}
+
+
+// When index is -1 index chooses the current tab
+void MainView::slotReloadTab(int index)
+{
+ if (index < 0)
+ index = currentIndex();
+ if (index < 0 || index >= count())
+ return;
+
+ QWidget *widget = this->widget(index);
+ if (WebView *tab = qobject_cast<WebView*>(widget))
+ tab->reload();
+}
+
+
+void MainView::slotCurrentChanged(int index)
+{
+ WebView *webView = this->webView(index);
+ if (!webView)
+ return;
+
+ Q_ASSERT(m_urlBars->count() == count());
+
+ WebView *oldWebView = this->webView(m_urlBars->currentIndex());
+ if (oldWebView)
+ {
+ disconnect(oldWebView, SIGNAL(statusBarMessage(const QString&)),
+ this, SIGNAL(showStatusBarMessage(const QString&)));
+ disconnect(oldWebView->page(), SIGNAL(linkHovered(const QString&, const QString&, const QString&)),
+ this, SIGNAL(linkHovered(const QString&)));
+ disconnect(oldWebView, SIGNAL(loadProgress(int)),
+ this, SIGNAL(loadProgress(int)));
+ }
+
+ connect(webView, SIGNAL(statusBarMessage(const QString&)), this, SIGNAL(showStatusBarMessage(const QString&)));
+ connect(webView->page(), SIGNAL(linkHovered(const QString&, const QString&, const QString&)), this, SIGNAL(linkHovered(const QString&)));
+ connect(webView, SIGNAL(loadProgress(int)), this, SIGNAL(loadProgress(int)));
+
+ emit setCurrentTitle(webView->title());
+ m_urlBars->setCurrentIndex(index);
+ emit loadProgress(webView->progress());
+ emit showStatusBarMessage(webView->lastStatusBarText());
+
+ // set focus to the current webview
+ webView->setFocus();
+}
+
+
+UrlBar *MainView::urlBar(int index) const
+{
+ if (index == -1)
+ {
+ index = m_urlBars->currentIndex();
+ }
+ UrlBar *urlBar = m_urlBars->urlBar(index);
+ if (urlBar)
+ {
+ return urlBar;
+ }
+ kWarning() << "URL bar with index" << index << "not found. Returning NULL. (line:" << __LINE__ << ")";
+ return NULL;
+}
+
+
+WebView *MainView::webView(int index) const
+{
+ QWidget *widget = this->widget(index);
+ if (WebView *webView = qobject_cast<WebView*>(widget))
+ {
+ return webView;
+ }
+
+ kWarning() << "WebView with index " << index << "not found. Returning NULL." ;
+ return 0;
+}
+
+
+WebView *MainView::newWebView(Rekonq::OpenType type)
+{
+ // line edit
+ UrlBar *urlBar = new UrlBar; // Ownership of widget is passed on to the QStackedWidget (addWidget method).
+ connect(urlBar, SIGNAL(activated(const KUrl&)), this, SLOT(loadUrl(const KUrl&)));
+ m_urlBars->addUrlBar(urlBar);
+
+ WebView *webView = new WebView; // should be deleted on tab close
+
+ // connecting webview with urlbar
+ connect(webView, SIGNAL(loadProgress(int)), urlBar, SLOT(slotUpdateProgress(int)));
+ connect(webView, SIGNAL(loadFinished(bool)), urlBar, SLOT(slotLoadFinished(bool)));
+ connect(webView, SIGNAL(urlChanged(const QUrl &)), urlBar, SLOT(setUrl(const QUrl &)));
+ connect(webView, SIGNAL(iconChanged()), urlBar, SLOT(slotUpdateUrl()));
+
+ // connecting webview with mainview
+ connect(webView, SIGNAL(loadStarted()), this, SLOT(webViewLoadStarted()));
+ connect(webView, SIGNAL(loadProgress(int)), this, SLOT(webViewLoadProgress(int)));
+ connect(webView, SIGNAL(loadFinished(bool)), this, SLOT(webViewLoadFinished(bool)));
+ connect(webView, SIGNAL(iconChanged()), this, SLOT(webViewIconChanged()));
+ connect(webView, SIGNAL(titleChanged(const QString &)), this, SLOT(webViewTitleChanged(const QString &)));
+ connect(webView, SIGNAL(urlChanged(const QUrl &)), this, SLOT(webViewUrlChanged(const QUrl &)));
+
+ connect(webView, SIGNAL(ctrlTabPressed()), this, SLOT(nextTab()));
+ connect(webView, SIGNAL(shiftCtrlTabPressed()), this, SLOT(previousTab()));
+
+ // connecting webPage signals with mainview
+ connect(webView->page(), SIGNAL(windowCloseRequested()),
+ this, SLOT(windowCloseRequested()));
+ connect(webView->page(), SIGNAL(geometryChangeRequested(const QRect &)),
+ this, SIGNAL(geometryChangeRequested(const QRect &)));
+ connect(webView->page(), SIGNAL(printRequested(QWebFrame *)),
+ this, SIGNAL(printRequested(QWebFrame *)));
+ connect(webView->page(), SIGNAL(menuBarVisibilityChangeRequested(bool)),
+ this, SIGNAL(menuBarVisibilityChangeRequested(bool)));
+ connect(webView->page(), SIGNAL(statusBarVisibilityChangeRequested(bool)),
+ this, SIGNAL(statusBarVisibilityChangeRequested(bool)));
+ connect(webView->page(), SIGNAL(toolBarVisibilityChangeRequested(bool)),
+ this, SIGNAL(toolBarVisibilityChangeRequested(bool)));
+
+ addTab(webView, i18n("(Untitled)"));
+
+ switch(type)
+ {
+ case Rekonq::Default:
+ if (!m_makeBackTab)
+ {
+ setCurrentWidget(webView); // this method does NOT take ownership of webView
+ urlBar->setFocus();
+ }
+ break;
+ case Rekonq::New:
+ setCurrentWidget(webView); // this method does NOT take ownership of webView
+ urlBar->setFocus();
+ break;
+ case Rekonq::Background:
+ break;
+ };
+
+ emit tabsChanged();
+
+ showTabBar();
+
+ return webView;
+}
+
+
+void MainView::slotReloadAllTabs()
+{
+ for (int i = 0; i < count(); ++i)
+ {
+ QWidget *tabWidget = widget(i);
+ if (WebView *tab = qobject_cast<WebView*>(tabWidget))
+ {
+ tab->reload();
+ }
+ }
+}
+
+
+void MainView::windowCloseRequested()
+{
+
+ WebPage *webPage = qobject_cast<WebPage*>(sender());
+ WebView *webView = qobject_cast<WebView*>(webPage->view());
+ int index = webViewIndex(webView);
+
+ if (index >= 0)
+ {
+ if (count() == 1)
+ {
+ Application::instance()->mainWindow()->close();
+ }
+ else
+ {
+ slotCloseTab(index);
+ }
+ }
+ else
+ {
+ kWarning() << "Invalid tab index" << "line:" << __LINE__;
+ }
+}
+
+
+void MainView::slotCloseOtherTabs(int index)
+{
+ if (-1 == index)
+ return;
+
+ for (int i = count() - 1; i > index; --i)
+ {
+ slotCloseTab(i);
+ }
+
+ for (int i = index - 1; i >= 0; --i)
+ {
+ slotCloseTab(i);
+ }
+
+ showTabBar();
+}
+
+
+// When index is -1 index chooses the current tab
+void MainView::slotCloneTab(int index)
+{
+ if (index < 0)
+ index = currentIndex();
+ if (index < 0 || index >= count())
+ return;
+ WebView *tab = newWebView();
+ tab->setUrl(webView(index)->url());
+
+ showTabBar();
+}
+
+
+// When index is -1 index chooses the current tab
+void MainView::slotCloseTab(int index)
+{
+ // do nothing if just one tab is opened
+ if (count() == 1)
+ return;
+
+ if (index < 0)
+ index = currentIndex();
+ if (index < 0 || index >= count())
+ return;
+
+ bool hasFocus = false;
+ if (WebView *tab = webView(index))
+ {
+ if (tab->isModified())
+ {
+ int risp = KMessageBox::questionYesNo(this ,
+ i18n("You have modified this page and when closing it you would lose the modification.\n"
+ "Do you really want to close this page?\n"),
+ i18n("Do you really want to close this page?")
+ );
+ if (risp == KMessageBox::No)
+ return;
+ }
+ hasFocus = tab->hasFocus();
+
+ m_recentlyClosedTabsAction->setEnabled(true);
+ m_recentlyClosedTabs.prepend(tab->url());
+
+ // don't add empty urls
+ if (tab->url().isValid())
+ {
+ m_recentlyClosedTabs.prepend(tab->url());
+ }
+
+ if (m_recentlyClosedTabs.size() >= MainView::m_recentlyClosedTabsSize)
+ {
+ m_recentlyClosedTabs.removeLast();
+ }
+ }
+
+ QWidget *urlBar = m_urlBars->urlBar(index);
+ m_urlBars->removeWidget(urlBar);
+ urlBar->deleteLater(); // urlBar is scheduled for deletion.
+
+ QWidget *webView = widget(index);
+ removeTab(index);
+ webView->deleteLater(); // webView is scheduled for deletion.
+
+ emit tabsChanged();
+
+ if (hasFocus && count() > 0)
+ {
+ currentWebView()->setFocus();
+ }
+
+ showTabBar();
+}
+
+
+void MainView::webViewLoadStarted()
+{
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+ if (-1 != index)
+ {
+ QLabel *label = animatedLoading(index, true);
+ if (label->movie())
+ {
+ label->movie()->start();
+ }
+ }
+
+ if (index != currentIndex())
+ return;
+
+ emit showStatusBarMessage(i18n("Loading..."));
+}
+
+
+void MainView::webViewLoadProgress(int progress)
+{
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+ if (index != currentIndex() || index < 0)
+ {
+ return;
+ }
+
+ double totalBytes = static_cast<double>(webView->webPage()->totalBytes() / 1024);
+
+ QString message = i18n("Loading %1% (%2 %3)...", progress, totalBytes, QLatin1String("kB"));
+ emit showStatusBarMessage(message);
+}
+
+
+void MainView::webViewLoadFinished(bool ok)
+{
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+
+ if (-1 != index)
+ {
+ QLabel *label = animatedLoading(index, true);
+ QMovie *movie = label->movie();
+ if (movie)
+ movie->stop();
+ }
+
+ webViewIconChanged();
+
+ // don't display messages for background tabs
+ if (index != currentIndex())
+ {
+ return;
+ }
+
+ if (ok)
+ emit showStatusBarMessage(i18n("Done"));
+ else
+ emit showStatusBarMessage(i18n("Failed to load"));
+}
+
+
+void MainView::webViewIconChanged()
+{
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+ if (-1 != index)
+ {
+ QIcon icon = Application::instance()->icon(webView->url());
+ QLabel *label = animatedLoading(index, false);
+ QMovie *movie = label->movie();
+ delete movie;
+ label->setMovie(0);
+ label->setPixmap(icon.pixmap(16, 16));
+ }
+}
+
+
+void MainView::webViewTitleChanged(const QString &title)
+{
+ QString tabTitle = title;
+ if (title.isEmpty())
+ {
+ tabTitle = i18n("(Untitled)");
+ }
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+ if (-1 != index)
+ {
+ setTabText(index, tabTitle);
+ }
+ if (currentIndex() == index)
+ {
+ emit setCurrentTitle(tabTitle);
+ }
+ Application::historyManager()->updateHistoryEntry(webView->url(), tabTitle);
+}
+
+
+void MainView::webViewUrlChanged(const QUrl &url)
+{
+ WebView *webView = qobject_cast<WebView*>(sender());
+ int index = webViewIndex(webView);
+ if (-1 != index)
+ {
+ m_tabBar->setTabData(index, url);
+ }
+ emit tabsChanged();
+}
+
+
+void MainView::aboutToShowRecentTabsMenu()
+{
+ m_recentlyClosedTabsMenu->clear();
+ for (int i = 0; i < m_recentlyClosedTabs.count(); ++i)
+ {
+ KAction *action = new KAction(m_recentlyClosedTabsMenu);
+ action->setData(m_recentlyClosedTabs.at(i));
+ QIcon icon = Application::instance()->icon(m_recentlyClosedTabs.at(i));
+ action->setIcon(icon);
+ action->setText(m_recentlyClosedTabs.at(i).prettyUrl());
+ m_recentlyClosedTabsMenu->addAction(action);
+ }
+}
+
+
+void MainView::aboutToShowRecentTriggeredAction(QAction *action)
+{
+ KUrl url = action->data().toUrl();
+ loadUrl(url);
+}
+
+
+void MainView::loadUrl(const KUrl &url)
+{
+ if (url.isEmpty())
+ return;
+
+ currentUrlBar()->setUrl(url.prettyUrl());
+
+ WebView *webView = currentWebView();
+
+ KUrl loadingUrl(url);
+
+ if (loadingUrl.isRelative())
+ {
+ QString fn = loadingUrl.url(KUrl::RemoveTrailingSlash);
+ loadingUrl.setUrl("//" + fn);
+ loadingUrl.setScheme("http");
+ }
+
+ if (webView)
+ {
+ webView->load(loadingUrl);
+ webView->setFocus();
+ }
+}
+
+
+void MainView::nextTab()
+{
+ int next = currentIndex() + 1;
+ if (next == count())
+ next = 0;
+ setCurrentIndex(next);
+}
+
+
+void MainView::previousTab()
+{
+ int next = currentIndex() - 1;
+ if (next < 0)
+ next = count() - 1;
+ setCurrentIndex(next);
+}
+
+
+void MainView::moveTab(int fromIndex, int toIndex)
+{
+ QWidget *lineEdit = m_urlBars->widget(fromIndex);
+ m_urlBars->removeWidget(lineEdit);
+ m_urlBars->insertWidget(toIndex, lineEdit);
+}
+
+
+QLabel *MainView::animatedLoading(int index, bool addMovie)
+{
+ if (index == -1)
+ return 0;
+
+ QLabel *label = qobject_cast<QLabel*>(m_tabBar->tabButton(index, QTabBar::LeftSide));
+ if (!label)
+ {
+ label = new QLabel(this);
+ }
+ if (addMovie && !label->movie())
+ {
+ QMovie *movie = new QMovie(m_loadingGitPath, QByteArray(), label);
+ movie->setSpeed(50);
+ label->setMovie(movie);
+ movie->start();
+ }
+ m_tabBar->setTabButton(index, QTabBar::LeftSide, 0);
+ m_tabBar->setTabButton(index, QTabBar::LeftSide, label);
+ return label;
+}
+
+
+void MainView::mouseDoubleClickEvent(QMouseEvent *event)
+{
+ if (!childAt(event->pos()))
+ {
+ newWebView(Rekonq::New);
+ return;
+ }
+ KTabWidget::mouseDoubleClickEvent(event);
+} \ No newline at end of file
diff --git a/src/mainview.h b/src/mainview.h
new file mode 100644
index 00000000..372902dd
--- /dev/null
+++ b/src/mainview.h
@@ -0,0 +1,198 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+
+#ifndef TABWIDGET_H
+#define TABWIDGET_H
+
+// Local Includes
+#include "webview.h"
+#include "application.h"
+
+// KDE Includes
+#include <KTabWidget>
+
+// Forward Declarations
+class QLineEdit;
+class QUrl;
+class QWebFrame;
+class QLabel;
+
+class KAction;
+class KCompletion;
+class KMenu;
+class KUrl;
+
+class HistoryCompletionModel;
+class StackedUrlBar;
+class TabBar;
+class UrlBar;
+
+
+/**
+ * This class represent rekonq Main View. It contains all WebViews and a stack widget
+ * of associated line edits.
+ *
+ */
+
+class MainView : public KTabWidget
+{
+ Q_OBJECT
+
+public:
+ MainView(QWidget *parent = 0);
+ ~MainView();
+
+public:
+
+ UrlBar *urlBar(int index) const;
+ UrlBar *currentUrlBar() const { return urlBar(-1); }
+ WebView *webView(int index) const;
+ QList<WebView *> tabs(); // ?
+
+ // inlines
+ TabBar *tabBar() const { return m_tabBar; }
+ StackedUrlBar *urlBarStack() const { return m_urlBars; }
+ WebView *currentWebView() const { return webView(currentIndex()); }
+ int webViewIndex(WebView *webView) const { return indexOf(webView); }
+ KAction *recentlyClosedTabsAction() const { return m_recentlyClosedTabsAction; }
+ void setMakeBackTab(bool b) { m_makeBackTab = b; }
+
+ /**
+ * show and hide TabBar if user doesn't choose
+ * "Always Show TabBar" option
+ *
+ */
+ void showTabBar();
+ void clear();
+
+
+signals:
+ // tab widget signals
+ void tabsChanged();
+ void lastTabClosed();
+
+ // current tab signals
+ void setCurrentTitle(const QString &url);
+ void showStatusBarMessage(const QString &message);
+ void linkHovered(const QString &link);
+ void loadProgress(int progress);
+
+ void geometryChangeRequested(const QRect &geometry);
+ void menuBarVisibilityChangeRequested(bool visible);
+ void statusBarVisibilityChangeRequested(bool visible);
+ void toolBarVisibilityChangeRequested(bool visible);
+ void printRequested(QWebFrame *frame);
+
+public slots:
+ /**
+ * Core browser slot. This create a new tab with a WebView inside
+ * for browsing.
+ *
+ * @return a pointer to the new WebView
+ */
+ WebView *newWebView(Rekonq::OpenType type = Rekonq::Default);
+
+ /**
+ * Core browser slot. Load an url in a webview
+ *
+ * @param url The url to load
+ */
+ void loadUrl(const KUrl &url);
+ void slotCloneTab(int index = -1);
+ void slotCloseTab(int index = -1);
+ void slotCloseOtherTabs(int index);
+ void slotReloadTab(int index = -1);
+ void slotReloadAllTabs();
+ void nextTab();
+ void previousTab();
+
+ // WEB slot actions
+ void slotWebReload();
+ void slotWebStop();
+ void slotWebBack();
+ void slotWebForward();
+ void slotWebUndo();
+ void slotWebRedo();
+ void slotWebCut();
+ void slotWebCopy();
+ void slotWebPaste();
+
+private slots:
+ void slotCurrentChanged(int index);
+ void aboutToShowRecentTabsMenu();
+ void aboutToShowRecentTriggeredAction(QAction *action); // need QAction!
+
+ void webViewLoadStarted();
+ void webViewLoadProgress(int progress);
+ void webViewLoadFinished(bool ok);
+ void webViewIconChanged();
+ void webViewTitleChanged(const QString &title);
+ void webViewUrlChanged(const QUrl &url);
+
+ void windowCloseRequested();
+
+ /**
+ * This functions move tab informations "from index to index"
+ *
+ * @param fromIndex the index from which we move
+ *
+ * @param toIndex the index to which we move
+ */
+ void moveTab(int fromIndex, int toIndex);
+
+ void postLaunch();
+
+protected:
+
+ virtual void mouseDoubleClickEvent(QMouseEvent *event);
+
+
+private:
+
+ /**
+ * This function creates (if not exists) and returns a QLabel
+ * with a loading QMovie.
+ * Imported from Arora's code.
+ *
+ * @param index the tab index where inserting the animated label
+ * @param addMovie creates or not a loading movie
+ *
+ * @return animated label's pointer
+ */
+ QLabel *animatedLoading(int index, bool addMovie);
+
+ static const int m_recentlyClosedTabsSize = 10;
+ KAction *m_recentlyClosedTabsAction;
+
+ KMenu *m_recentlyClosedTabsMenu;
+ QList<KUrl> m_recentlyClosedTabs;
+
+ StackedUrlBar *m_urlBars;
+ TabBar *m_tabBar;
+
+ QString m_loadingGitPath;
+
+ bool m_makeBackTab;
+};
+
+#endif
diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp
new file mode 100644
index 00000000..d1ab721f
--- /dev/null
+++ b/src/mainwindow.cpp
@@ -0,0 +1,930 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "mainwindow.h"
+#include "mainwindow.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "application.h"
+#include "settings.h"
+#include "history.h"
+#include "cookiejar.h"
+#include "networkaccessmanager.h"
+#include "bookmarks.h"
+#include "webview.h"
+#include "mainview.h"
+#include "bookmarks.h"
+#include "download.h"
+#include "findbar.h"
+#include "sidepanel.h"
+#include "urlbar.h"
+#include "stackedurlbar.h"
+
+// KDE Includes
+#include <KUrl>
+#include <KStatusBar>
+#include <KMenuBar>
+#include <KShortcut>
+#include <KStandardAction>
+#include <KAction>
+#include <KToggleFullScreenAction>
+#include <KActionCollection>
+#include <KMessageBox>
+#include <KFileDialog>
+#include <KMenu>
+#include <KGlobalSettings>
+#include <KPushButton>
+#include <KTemporaryFile>
+
+#include <kdeprintdialog.h>
+#include <kprintpreview.h>
+
+
+// Qt Includes
+#include <QtGui>
+#include <QtCore>
+#include <QtWebKit>
+
+
+MainWindow::MainWindow()
+ : KXmlGuiWindow()
+ , m_view(new MainView(this))
+ , m_findBar(new FindBar(this))
+ , m_searchBar(new SearchBar(this))
+ , m_sidePanel(0)
+{
+ // updating rekonq configuration
+ slotUpdateConfiguration();
+
+ // creating a centralWidget containing panel, m_view and the hidden findbar
+ QWidget *centralWidget = new QWidget;
+ centralWidget->setContentsMargins(0, 0, 0, 0);
+
+ // setting layout
+ QVBoxLayout *layout = new QVBoxLayout;
+ layout->setContentsMargins(0, 0, 0, 0);
+ layout->addWidget(m_view);
+ layout->addWidget(m_findBar);
+ centralWidget->setLayout(layout);
+
+ // central widget
+ setCentralWidget(centralWidget);
+
+ // setting size policies
+ setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
+
+ // then, setup our actions
+ setupActions();
+
+ // setting up toolbars: this has to be done BEFORE setupGUI!!
+ setupToolBars();
+
+ // Bookmark Menu
+ KActionMenu *bmMenu = Application::bookmarkProvider()->bookmarkActionMenu();
+ actionCollection()->addAction(QLatin1String("bookmarks"), bmMenu);
+
+ // Side Panel: this has to be done BEFORE setupGUI!!
+ setupSidePanel();
+
+ // a call to KXmlGuiWindow::setupGUI() populates the GUI
+ // with actions, using KXMLGUI.
+ // It also applies the saved mainwindow settings, if any, and ask the
+ // mainwindow to automatically save settings if changed: window size,
+ // toolbar position, icon size, etc.
+ setupGUI();
+
+ QTimer::singleShot(0, this, SLOT(postLaunch()));
+}
+
+
+MainWindow::~MainWindow()
+{
+ delete m_view;
+}
+
+
+void MainWindow::postLaunch()
+{
+ // setup history menu: this has to be done AFTER setupGUI!!
+ setupHistoryMenu();
+
+ // --------- connect signals and slots
+ connect(m_view, SIGNAL(setCurrentTitle(const QString &)), this, SLOT(slotUpdateWindowTitle(const QString &)));
+ connect(m_view, SIGNAL(loadProgress(int)), this, SLOT(slotLoadProgress(int)));
+ connect(m_view, SIGNAL(geometryChangeRequested(const QRect &)), this, SLOT(geometryChangeRequested(const QRect &)));
+ connect(m_view, SIGNAL(printRequested(QWebFrame *)), this, SLOT(printRequested(QWebFrame *)));
+ connect(m_view, SIGNAL(menuBarVisibilityChangeRequested(bool)), menuBar(), SLOT(setVisible(bool)));
+ connect(m_view, SIGNAL(statusBarVisibilityChangeRequested(bool)), statusBar(), SLOT(setVisible(bool)));
+
+ // status bar messages
+ connect(m_view, SIGNAL(showStatusBarMessage(const QString&)), statusBar(), SLOT(showMessage(const QString&)));
+ connect(m_view, SIGNAL(linkHovered(const QString&)), statusBar(), SLOT(showMessage(const QString&)));
+
+ // update toolbar actions signals
+ connect(m_view, SIGNAL(tabsChanged()), this, SLOT(slotUpdateActions()));
+ connect(m_view, SIGNAL(currentChanged(int)), this, SLOT(slotUpdateActions()));
+
+ // Find Bar signal
+ connect(m_findBar, SIGNAL(searchString(const QString &)), this, SLOT(slotFind(const QString &)));
+
+ // bookmarks loading
+ connect(Application::bookmarkProvider(), SIGNAL(openUrl(const KUrl&)), this, SLOT(loadUrl(const KUrl&)));
+
+ // setting up toolbars to NOT have context menu enabled
+ setContextMenuPolicy(Qt::DefaultContextMenu);
+
+ // accept d'n'd
+ setAcceptDrops(true);
+}
+
+
+QSize MainWindow::sizeHint() const
+{
+ QRect desktopRect = QApplication::desktop()->screenGeometry();
+ QSize size = desktopRect.size() * 0.8;
+ return size;
+}
+
+
+void MainWindow::setupToolBars()
+{
+ KAction *a;
+
+ // location bar
+ a = new KAction(i18n("Location Bar"), this);
+ a->setShortcut(KShortcut(Qt::Key_F6));
+ a->setDefaultWidget(m_view->urlBarStack());
+ actionCollection()->addAction(QLatin1String("url_bar"), a);
+
+ // search bar
+ a = new KAction(i18n("Search Bar"), this);
+ a->setShortcut(KShortcut(Qt::CTRL + Qt::Key_K));
+ a->setDefaultWidget(m_searchBar);
+ connect(m_searchBar, SIGNAL(search(const KUrl&)), this, SLOT(loadUrl(const KUrl&)));
+ actionCollection()->addAction(QLatin1String("search_bar"), a);
+
+ // bookmarks bar
+ KAction *bookmarkBarAction = Application::bookmarkProvider()->bookmarkToolBarAction();
+ a = actionCollection()->addAction(QLatin1String("bookmarks_bar"), bookmarkBarAction);
+}
+
+
+void MainWindow::setupActions()
+{
+ KAction *a;
+
+ // Standard Actions
+ KStandardAction::open(this, SLOT(slotFileOpen()), actionCollection());
+ KStandardAction::saveAs(this, SLOT(slotFileSaveAs()), actionCollection());
+ KStandardAction::printPreview(this, SLOT(slotFilePrintPreview()), actionCollection());
+ KStandardAction::print(this, SLOT(slotFilePrint()), actionCollection());
+ KStandardAction::quit(this , SLOT(close()), actionCollection());
+ KStandardAction::find(this, SLOT(slotViewFindBar()) , actionCollection());
+ KStandardAction::findNext(this, SLOT(slotFindNext()) , actionCollection());
+ KStandardAction::findPrev(this, SLOT(slotFindPrevious()) , actionCollection());
+ KStandardAction::fullScreen(this, SLOT(slotViewFullScreen(bool)), this, actionCollection());
+ KStandardAction::home(this, SLOT(slotHome()), actionCollection());
+ KStandardAction::preferences(this, SLOT(slotPreferences()), actionCollection());
+ KStandardAction::showMenubar(this, SLOT(slotShowMenubar(bool)), actionCollection());
+
+ // WEB Actions (NO KStandardActions..)
+ a = KStandardAction::redisplay(m_view, SLOT(slotWebReload()), actionCollection());
+ a->setText(i18n("Reload"));
+ KStandardAction::back(m_view, SLOT(slotWebBack()), actionCollection());
+ KStandardAction::forward(m_view, SLOT(slotWebForward()), actionCollection());
+ KStandardAction::undo(m_view, SLOT(slotWebUndo()), actionCollection());
+ KStandardAction::redo(m_view, SLOT(slotWebRedo()), actionCollection());
+ KStandardAction::cut(m_view, SLOT(slotWebCut()), actionCollection());
+ KStandardAction::copy(m_view, SLOT(slotWebCopy()), actionCollection());
+ KStandardAction::paste(m_view, SLOT(slotWebPaste()), actionCollection());
+
+ a = new KAction(KIcon("process-stop"), i18n("&Stop"), this);
+ a->setShortcut(KShortcut(Qt::CTRL | Qt::Key_Period));
+ actionCollection()->addAction(QLatin1String("stop"), a);
+ connect(a, SIGNAL(triggered(bool)), m_view, SLOT(slotWebStop()));
+
+ // stop reload Action
+ m_stopReloadAction = new KAction(KIcon("view-refresh"), i18n("Reload"), this);
+ actionCollection()->addAction(QLatin1String("stop_reload") , m_stopReloadAction);
+ m_stopReloadAction->setShortcutConfigurable(false);
+
+ // ============== Custom Actions
+ a = new KAction(KIcon("document-open-remote"), i18n("Open Location"), this);
+ a->setShortcut(Qt::CTRL + Qt::Key_L);
+ actionCollection()->addAction(QLatin1String("open_location"), a);
+ connect(a, SIGNAL(triggered(bool)) , this, SLOT(slotOpenLocation()));
+
+ a = new KAction(KIcon("zoom-in"), i18n("&Enlarge Font"), this);
+ a->setShortcut(KShortcut(Qt::CTRL | Qt::Key_Plus));
+ actionCollection()->addAction(QLatin1String("bigger_font"), a);
+ connect(a, SIGNAL(triggered(bool)), this, SLOT(slotViewTextBigger()));
+
+ a = new KAction(KIcon("zoom-original"), i18n("&Normal Font"), this);
+ a->setShortcut(KShortcut(Qt::CTRL | Qt::Key_0));
+ actionCollection()->addAction(QLatin1String("normal_font"), a);
+ connect(a, SIGNAL(triggered(bool)), this, SLOT(slotViewTextNormal()));
+
+ a = new KAction(KIcon("zoom-out"), i18n("&Shrink Font"), this);
+ a->setShortcut(KShortcut(Qt::CTRL | Qt::Key_Minus));
+ actionCollection()->addAction(QLatin1String("smaller_font"), a);
+ connect(a, SIGNAL(triggered(bool)), this, SLOT(slotViewTextSmaller()));
+
+ a = new KAction(i18n("Page S&ource"), this);
+ actionCollection()->addAction(QLatin1String("page_source"), a);
+ connect(a, SIGNAL(triggered(bool)), this, SLOT(slotViewPageSource()));
+
+ // ================ Tools (WebKit) Actions
+ a = new KAction(KIcon("tools-report-bug"), i18n("Web &Inspector"), this);
+ a->setCheckable(true);
+ actionCollection()->addAction(QLatin1String("web_inspector"), a);
+ connect(a, SIGNAL(triggered(bool)), this, SLOT(slotToggleInspector(bool)));
+
+ a = new KAction(KIcon("view-media-artist"), i18n("Private &Browsing"), this);
+ a->setCheckable(true);
+ actionCollection()->addAction(QLatin1String("private_browsing"), a);
+ connect(a, SIGNAL(triggered(bool)) , this, SLOT(slotPrivateBrowsing(bool)));
+
+ // ================ history related actions
+ m_historyBackAction = new KAction(KIcon("go-previous"), i18n("Back"), this);
+ m_historyBackMenu = new KMenu(this);
+ m_historyBackAction->setMenu(m_historyBackMenu);
+ connect(m_historyBackAction, SIGNAL(triggered(bool)), this, SLOT(slotOpenPrevious()));
+ connect(m_historyBackMenu, SIGNAL(aboutToShow()), this, SLOT(slotAboutToShowBackMenu()));
+ connect(m_historyBackMenu, SIGNAL(triggered(QAction *)), this, SLOT(slotOpenActionUrl(QAction *)));
+ actionCollection()->addAction(QLatin1String("history_back"), m_historyBackAction);
+
+ m_historyForwardAction = new KAction(KIcon("go-next"), i18n("Forward"), this);
+ connect(m_historyForwardAction, SIGNAL(triggered(bool)), this, SLOT(slotOpenNext()));
+ actionCollection()->addAction(QLatin1String("history_forward"), m_historyForwardAction);
+
+ // =================== Tab Actions
+ a = new KAction(KIcon("tab-new"), i18n("New &Tab"), this);
+ QList<QKeySequence> newTabShortcutList;
+ newTabShortcutList << QKeySequence(QKeySequence::New);
+ newTabShortcutList << QKeySequence(QKeySequence::AddTab);
+ a->setShortcut(KShortcut(newTabShortcutList));
+ actionCollection()->addAction(QLatin1String("new_tab"), a);
+ connect(a, SIGNAL(triggered(bool)), m_view, SLOT(newWebView()));
+
+ a = new KAction(KIcon("tab-close"), i18n("&Close Tab"), this);
+ a->setShortcut(KShortcut(Qt::CTRL + Qt::Key_W));
+ actionCollection()->addAction(QLatin1String("close_tab"), a);
+ connect(a, SIGNAL(triggered(bool)), m_view, SLOT(slotCloseTab()));
+
+ a = new KAction(i18n("Show Next Tab"), this);
+ a->setShortcuts(QApplication::isRightToLeft() ? KStandardShortcut::tabPrev() : KStandardShortcut::tabNext());
+ actionCollection()->addAction(QLatin1String("show_next_tab"), a);
+ connect(a, SIGNAL(triggered(bool)), m_view, SLOT(nextTab()));
+
+ a = new KAction(i18n("Show Previous Tab"), this);
+ a->setShortcuts(QApplication::isRightToLeft() ? KStandardShortcut::tabNext() : KStandardShortcut::tabPrev());
+ actionCollection()->addAction(QLatin1String("show_prev_tab"), a);
+ connect(a, SIGNAL(triggered(bool)), m_view, SLOT(previousTab()));
+}
+
+
+void MainWindow::setupSidePanel()
+{
+ // Setup history side panel
+ m_sidePanel = new SidePanel(i18n("History"), this);
+ connect(m_sidePanel, SIGNAL(openUrl(const KUrl&)), this, SLOT(loadUrl(const KUrl&)));
+ connect(m_sidePanel, SIGNAL(destroyed()), Application::instance(), SLOT(slotSaveConfiguration()));
+
+ addDockWidget(Qt::LeftDockWidgetArea, m_sidePanel);
+
+ // setup side panel actions
+ KAction* a = new KAction(this);
+ a->setText(i18n("History"));
+ a->setCheckable(true);
+ a->setChecked(ReKonfig::showSideBar());
+ a->setShortcut(KShortcut(Qt::CTRL + Qt::Key_H));
+ actionCollection()->addAction(QLatin1String("show_history_panel"), a);
+
+ // connect to toogle action
+ connect(a, SIGNAL(triggered(bool)), m_sidePanel->toggleViewAction(), SLOT(trigger()));
+}
+
+
+void MainWindow::setupHistoryMenu()
+{
+ HistoryMenu *historyMenu = new HistoryMenu(this);
+ connect(historyMenu, SIGNAL(openUrl(const KUrl&)), this, SLOT(loadUrl(const KUrl&)));
+ connect(historyMenu, SIGNAL(hovered(const QString&)), this, SLOT(slotUpdateStatusbar(const QString&)));
+ historyMenu->setTitle(i18n("&History"));
+
+ // setting history menu position
+ menuBar()->insertMenu(actionCollection()->action("bookmarks"), historyMenu);
+
+ // setting initial actions
+ QList<QAction*> historyActions;
+ historyActions.append(actionCollection()->action("history_back"));
+ historyActions.append(actionCollection()->action("history_forward"));
+ historyActions.append(m_view->recentlyClosedTabsAction());
+ historyMenu->setInitialActions(historyActions);
+}
+
+
+void MainWindow::slotUpdateConfiguration()
+{
+ // ============== General ==================
+ m_homePage = ReKonfig::homePage();
+ mainView()->showTabBar();
+ mainView()->setMakeBackTab( ReKonfig::openTabsBack() );
+
+ // =========== Fonts ==============
+ QWebSettings *defaultSettings = QWebSettings::globalSettings();
+
+ int fnSize = ReKonfig::fontSize();
+
+ QFont standardFont = ReKonfig::standardFont();
+ defaultSettings->setFontFamily(QWebSettings::StandardFont, standardFont.family());
+ defaultSettings->setFontSize(QWebSettings::DefaultFontSize, fnSize);
+
+ QFont fixedFont = ReKonfig::fixedFont();
+ defaultSettings->setFontFamily(QWebSettings::FixedFont, fixedFont.family());
+ defaultSettings->setFontSize(QWebSettings::DefaultFixedFontSize, fnSize);
+
+ // ================ WebKit ============================
+ defaultSettings->setAttribute(QWebSettings::AutoLoadImages, ReKonfig::autoLoadImages());
+ defaultSettings->setAttribute(QWebSettings::JavascriptEnabled, ReKonfig::javascriptEnabled());
+ defaultSettings->setAttribute(QWebSettings::JavaEnabled, ReKonfig::javaEnabled());
+ defaultSettings->setAttribute(QWebSettings::PluginsEnabled, ReKonfig::pluginsEnabled());
+ defaultSettings->setAttribute(QWebSettings::JavascriptCanOpenWindows, ReKonfig::javascriptCanOpenWindows());
+ defaultSettings->setAttribute(QWebSettings::JavascriptCanAccessClipboard, ReKonfig::javascriptCanAccessClipboard());
+ defaultSettings->setAttribute(QWebSettings::LinksIncludedInFocusChain, ReKonfig::linksIncludedInFocusChain());
+ defaultSettings->setAttribute(QWebSettings::ZoomTextOnly, ReKonfig::zoomTextOnly());
+ defaultSettings->setAttribute(QWebSettings::PrintElementBackgrounds, ReKonfig::printElementBackgrounds());
+ defaultSettings->setAttribute(QWebSettings::OfflineStorageDatabaseEnabled, ReKonfig::offlineStorageDatabaseEnabled());
+ defaultSettings->setAttribute(QWebSettings::OfflineWebApplicationCacheEnabled, ReKonfig::offlineWebApplicationCacheEnabled());
+ defaultSettings->setAttribute(QWebSettings::LocalStorageDatabaseEnabled, ReKonfig::localStorageDatabaseEnabled());
+
+ // ====== load Settings on main classes
+ Application::networkAccessManager()->loadSettings();
+ Application::cookieJar()->loadSettings();
+ Application::historyManager()->loadSettings();
+}
+
+
+void MainWindow::slotUpdateBrowser()
+{
+ slotUpdateConfiguration();
+ mainView()->slotReloadAllTabs();
+}
+
+
+KUrl MainWindow::guessUrlFromString(const QString &string)
+{
+ QString urlStr = string.trimmed();
+ QRegExp test(QLatin1String("^[a-zA-Z]+\\:.*"));
+
+ // Check if it looks like a qualified URL. Try parsing it and see.
+ bool hasSchema = test.exactMatch(urlStr);
+
+ if (hasSchema)
+ {
+ QUrl qurl(urlStr, QUrl::TolerantMode);
+ KUrl url(qurl);
+
+ if (url.isValid())
+ {
+ return url;
+ }
+ }
+
+ // Might be a file.
+ if (QFile::exists(urlStr))
+ {
+ QFileInfo info(urlStr);
+ return KUrl::fromPath(info.absoluteFilePath());
+ }
+
+ // Might be a shorturl - try to detect the schema.
+ if (!hasSchema)
+ {
+ int dotIndex = urlStr.indexOf(QLatin1Char('.'));
+
+ if (dotIndex != -1)
+ {
+ QString prefix = urlStr.left(dotIndex).toLower();
+ QString schema = (prefix == QLatin1String("ftp")) ? prefix : QLatin1String("http");
+ QUrl qurl(schema + QLatin1String("://") + urlStr, QUrl::TolerantMode);
+ KUrl url(qurl);
+
+ if (url.isValid())
+ {
+ return url;
+ }
+ }
+ }
+
+ // Fall back to QUrl's own tolerant parser.
+ QUrl qurl = QUrl(string, QUrl::TolerantMode);
+ KUrl url(qurl);
+
+ // finally for cases where the user just types in a hostname add http
+ if (qurl.scheme().isEmpty())
+ {
+ qurl = QUrl(QLatin1String("http://") + string, QUrl::TolerantMode);
+ url = KUrl(qurl);
+ }
+ return url;
+}
+
+
+void MainWindow::loadUrl(const KUrl &url)
+{
+ m_view->loadUrl(url);
+}
+
+
+void MainWindow::slotOpenLocation()
+{
+ m_view->currentUrlBar()->selectAll();
+ m_view->currentUrlBar()->setFocus();
+}
+
+
+void MainWindow::slotFileSaveAs()
+{
+ KUrl srcUrl = currentTab()->url();
+ Application::downloadManager()->newDownload(srcUrl);
+}
+
+
+void MainWindow::slotPreferences()
+{
+ // an instance the dialog could be already created and could be cached,
+ // in which case you want to display the cached dialog
+ if (SettingsDialog::showDialog("rekonfig"))
+ return;
+
+ // we didn't find an instance of this dialog, so lets create it
+ SettingsDialog *s = new SettingsDialog(this);
+
+ // keep us informed when the user changes settings
+ connect(s, SIGNAL(settingsChanged(const QString&)), this, SLOT(slotUpdateBrowser()));
+
+ s->exec();
+}
+
+
+void MainWindow::slotUpdateStatusbar(const QString &string)
+{
+ statusBar()->showMessage(string, 2000);
+}
+
+
+void MainWindow::slotUpdateActions()
+{
+ m_historyBackAction->setEnabled(currentTab()->history()->canGoBack());
+ m_historyForwardAction->setEnabled(currentTab()->history()->canGoForward());
+}
+
+
+void MainWindow::slotUpdateWindowTitle(const QString &title)
+{
+ if (title.isEmpty())
+ {
+ setWindowTitle("rekonq");
+ }
+ else
+ {
+ setWindowTitle(title + " - rekonq");
+ }
+}
+
+
+void MainWindow::slotFileOpen()
+{
+ QString filePath = KFileDialog::getOpenFileName(KUrl(),
+ i18n("Web Resources (*.html *.htm *.svg *.png *.gif *.svgz); All files (*.*)"),
+ this,
+ i18n("Open Web Resource")
+ );
+
+ if (filePath.isEmpty())
+ return;
+
+ loadUrl(guessUrlFromString(filePath));
+}
+
+
+void MainWindow::slotFilePrintPreview()
+{
+ if (!currentTab())
+ return;
+
+ QPrinter printer;
+ KPrintPreview previewdlg(&printer, this);
+ currentTab()->print(&printer);
+ previewdlg.exec();
+}
+
+
+void MainWindow::slotFilePrint()
+{
+ if (!currentTab())
+ return;
+ printRequested(currentTab()->page()->mainFrame());
+}
+
+
+void MainWindow::printRequested(QWebFrame *frame)
+{
+ QPrinter printer;
+
+ QPrintDialog *dialog = KdePrint::createPrintDialog(&printer, this);
+ if (dialog->exec() != QDialog::Accepted)
+ return;
+ frame->print(&printer);
+}
+
+
+void MainWindow::slotPrivateBrowsing(bool enable)
+{
+ QWebSettings *settings = QWebSettings::globalSettings();
+ if (enable)
+ {
+ QString title = i18n("Are you sure you want to turn on private browsing?");
+ QString text = "<b>" + title + i18n("</b><br><br>When private browsing in turned on,"
+ " webpages are not added to the history,"
+ " new cookies are not stored, current cookies cannot be accessed," \
+ " site icons will not be stored, session will not be saved, " \
+ " and searches are not addded to the pop-up menu in the Google search box." \
+ " Until you close the window, you can still click the Back and Forward buttons" \
+ " to return to the webpages you have opened.");
+
+ int button = KMessageBox::questionYesNo(this, text, title);
+ if (button == KMessageBox::Ok)
+ {
+ settings->setAttribute(QWebSettings::PrivateBrowsingEnabled, true);
+ }
+ else
+ {
+ actionCollection()->action("private_browsing")->setChecked(false);
+ }
+ }
+ else
+ {
+ settings->setAttribute(QWebSettings::PrivateBrowsingEnabled, false);
+
+ MainWindow* win = Application::instance()->mainWindow();
+ win->m_lastSearch = QString::null;
+ win->mainView()->clear();
+ }
+}
+
+void MainWindow::slotFind(const QString & search)
+{
+ if (!currentTab())
+ return;
+ m_lastSearch = search;
+ slotFindNext();
+}
+
+
+void MainWindow::slotViewFindBar()
+{
+ m_findBar->showFindBar();
+}
+
+
+void MainWindow::slotFindNext()
+{
+ if (!currentTab() && m_lastSearch.isEmpty())
+ return;
+
+ QWebPage::FindFlags options;
+ if (m_findBar->matchCase())
+ {
+ options = QWebPage::FindCaseSensitively | QWebPage::FindWrapsAroundDocument;
+ }
+ else
+ {
+ options = QWebPage::FindWrapsAroundDocument;
+ }
+
+ if (!currentTab()->findText(m_lastSearch, options))
+ {
+ slotUpdateStatusbar(QString(m_lastSearch) + i18n(" not found."));
+ }
+}
+
+
+void MainWindow::slotFindPrevious()
+{
+ if (!currentTab() && m_lastSearch.isEmpty())
+ return;
+
+ QWebPage::FindFlags options;
+ if (m_findBar->matchCase())
+ {
+ options = QWebPage::FindCaseSensitively | QWebPage::FindBackward | QWebPage::FindWrapsAroundDocument;
+ }
+ else
+ {
+ options = QWebPage::FindBackward | QWebPage::FindWrapsAroundDocument;
+ }
+
+ if (!currentTab()->findText(m_lastSearch, options))
+ {
+ slotUpdateStatusbar(QString(m_lastSearch) + i18n(" not found."));
+ }
+}
+
+
+void MainWindow::slotViewTextBigger()
+{
+ if (!currentTab())
+ return;
+ currentTab()->setTextSizeMultiplier(currentTab()->textSizeMultiplier() + 0.1);
+}
+
+
+void MainWindow::slotViewTextNormal()
+{
+ if (!currentTab())
+ return;
+ currentTab()->setTextSizeMultiplier(1.0);
+}
+
+
+void MainWindow::slotViewTextSmaller()
+{
+ if (!currentTab())
+ return;
+ currentTab()->setTextSizeMultiplier(currentTab()->textSizeMultiplier() - 0.1);
+}
+
+
+void MainWindow::slotViewFullScreen(bool makeFullScreen)
+{
+ // state flags
+ static bool menubarFlag;
+ static bool mainToolBarFlag;
+ static bool bookmarksToolBarFlag;
+ static bool statusBarFlag;
+ static bool sidePanelFlag;
+
+ if (makeFullScreen == true)
+ {
+ // save current state
+ menubarFlag = menuBar()->isHidden();
+ mainToolBarFlag = toolBar("mainToolBar")->isHidden();
+ bookmarksToolBarFlag = toolBar("bookmarksToolBar")->isHidden();
+ statusBarFlag = statusBar()->isHidden();
+ sidePanelFlag = sidePanel()->isHidden();
+
+ menuBar()->hide();
+ toolBar("mainToolBar")->hide();
+ toolBar("bookmarksToolBar")->hide();
+ statusBar()->hide();
+ sidePanel()->hide();
+ }
+ else
+ {
+ if (!menubarFlag)
+ menuBar()->show();
+ if (!mainToolBarFlag)
+ toolBar("mainToolBar")->show();
+ if (!bookmarksToolBarFlag)
+ toolBar("bookmarksToolBar")->show();
+ if (!statusBarFlag)
+ statusBar()->show();
+ if (!sidePanelFlag)
+ sidePanel()->show();
+ }
+
+ KToggleFullScreenAction::setFullScreen(this, makeFullScreen);
+}
+
+
+void MainWindow::slotViewPageSource()
+{
+ if (!currentTab())
+ return;
+
+ KUrl url(currentTab()->url());
+ bool isTempFile = false;
+ if (!url.isLocalFile())
+ {
+ KTemporaryFile sourceFile;
+
+ /// TODO: autochoose tempfile suffix
+ sourceFile.setSuffix(QString(".html"));
+ sourceFile.setAutoRemove(false);
+
+ if (sourceFile.open())
+ {
+ QDataStream stream(&sourceFile);
+ stream << currentTab()->page()->mainFrame()->toHtml().toUtf8();
+
+ url = KUrl();
+ url.setPath(sourceFile.fileName());
+ isTempFile = true;
+ }
+ }
+ KRun::runUrl(url, QLatin1String("text/plain"), this, isTempFile);
+}
+
+
+void MainWindow::slotHome()
+{
+ loadUrl(KUrl(m_homePage));
+}
+
+
+void MainWindow::slotToggleInspector(bool enable)
+{
+ QWebSettings::globalSettings()->setAttribute(QWebSettings::DeveloperExtrasEnabled, enable);
+ if (enable)
+ {
+ int result = KMessageBox::questionYesNo(this,
+ i18n("The web inspector will only work correctly for pages that were loaded after enabling.\n"
+ "Do you want to reload all pages?"),
+ i18n("Web Inspector")
+ );
+
+ if (result == KMessageBox::Yes)
+ {
+ m_view->slotReloadAllTabs();
+ }
+ }
+}
+
+
+MainView *MainWindow::mainView() const
+{
+ return m_view;
+}
+
+
+
+WebView *MainWindow::currentTab() const
+{
+ return m_view->currentWebView();
+}
+
+
+void MainWindow::slotLoadProgress(int progress)
+{
+ QAction *stop = actionCollection()->action("stop");
+ QAction *reload = actionCollection()->action("view_redisplay");
+ if (progress < 100 && progress > 0)
+ {
+ disconnect(m_stopReloadAction, SIGNAL(triggered(bool)), reload , SIGNAL(triggered(bool)));
+ m_stopReloadAction->setIcon(KIcon("process-stop"));
+ m_stopReloadAction->setToolTip(i18n("Stop loading the current page"));
+ m_stopReloadAction->setText(i18n("Stop"));
+ connect(m_stopReloadAction, SIGNAL(triggered(bool)), stop, SIGNAL(triggered(bool)));
+ }
+ else
+ {
+ disconnect(m_stopReloadAction, SIGNAL(triggered(bool)), stop , SIGNAL(triggered(bool)));
+ m_stopReloadAction->setIcon(KIcon("view-refresh"));
+ m_stopReloadAction->setToolTip(i18n("Reload the current page"));
+ m_stopReloadAction->setText(i18n("Reload"));
+ connect(m_stopReloadAction, SIGNAL(triggered(bool)), reload, SIGNAL(triggered(bool)));
+
+ }
+}
+
+
+void MainWindow::slotAboutToShowBackMenu()
+{
+ m_historyBackMenu->clear();
+ if (!currentTab())
+ return;
+ QWebHistory *history = currentTab()->history();
+ int historyCount = history->count();
+ for (int i = history->backItems(historyCount).count() - 1; i >= 0; --i)
+ {
+ QWebHistoryItem item = history->backItems(history->count()).at(i);
+ KAction *action = new KAction(this);
+ action->setData(-1*(historyCount - i - 1));
+ QIcon icon = Application::instance()->icon(item.url());
+ action->setIcon(icon);
+ action->setText(item.title());
+ m_historyBackMenu->addAction(action);
+ }
+}
+
+
+void MainWindow::slotOpenActionUrl(QAction *action)
+{
+ int offset = action->data().toInt();
+ QWebHistory *history = currentTab()->history();
+ if (offset < 0)
+ {
+ history->goToItem(history->backItems(-1*offset).first()); // back
+ }
+ else
+ {
+ if (offset > 0)
+ {
+ history->goToItem(history->forwardItems(history->count() - offset + 1).back()); // forward
+ }
+ }
+}
+
+
+void MainWindow::slotOpenPrevious()
+{
+ QWebHistory *history = currentTab()->history();
+ if (history->canGoBack())
+ history->goToItem(history->backItem());
+}
+
+
+void MainWindow::slotOpenNext()
+{
+ QWebHistory *history = currentTab()->history();
+ if (history->canGoForward())
+ history->goToItem(history->forwardItem());
+}
+
+
+void MainWindow::geometryChangeRequested(const QRect &geometry)
+{
+ setGeometry(geometry);
+}
+
+
+void MainWindow::slotShowMenubar(bool enable)
+{
+ if (enable)
+ menuBar()->show();
+ else
+ menuBar()->hide();
+}
+
+
+bool MainWindow::queryClose()
+{
+ if (m_view->count() > 1)
+ {
+
+ int answer = KMessageBox::questionYesNoCancel(
+ this,
+ i18np("Are you sure you want to close the window?\n" "You have 1 tab open","Are you sure you want to close the window?\n" "You have %1 tabs open" , m_view->count()),
+ i18n("Are you sure you want to close the window?"),
+ KStandardGuiItem::quit(),
+ KGuiItem(i18n("C&lose Current Tab"), KIcon("tab-close")),
+ KStandardGuiItem::cancel(),
+ "confirmClosingMultipleTabs"
+ );
+
+ switch (answer)
+ {
+ case KMessageBox::Yes:
+ // Quit
+ return true;
+ break;
+ case KMessageBox::No:
+ // Close only the current tab
+ m_view->slotCloseTab();
+ default:
+ return false;
+ }
+ }
+
+ return true;
+}
+
+
+QAction *MainWindow::actionByName(const QString name)
+{
+ QAction *ret = actionCollection()->action(name);
+
+ if (ret)
+ return ret;
+
+ /* else */
+ kWarning() << "Action named: " << name << " not found, returning empty action.";
+
+ return new QAction(this); // return empty object instead of NULL pointer
+}
+
diff --git a/src/mainwindow.h b/src/mainwindow.h
new file mode 100644
index 00000000..cdb7151d
--- /dev/null
+++ b/src/mainwindow.h
@@ -0,0 +1,153 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef MAINWINDOW_H
+#define MAINWINDOW_H
+
+// Local Includes
+#include "searchbar.h"
+#include "bookmarks.h"
+#include "mainview.h"
+#include "webview.h"
+
+// KDE Includes
+#include <KXmlGuiWindow>
+#include <KToolBar>
+
+// Forward Declarations
+class QWebFrame;
+
+class KUrl;
+class KAction;
+class KActionMenu;
+class KIcon;
+class KMenu;
+
+class FindBar;
+class HistoryMenu;
+class SidePanel;
+class WebView;
+
+
+/**
+ * This class serves as the main window for rekonq.
+ * It handles the menus, toolbars, and status bars.
+ *
+ */
+class MainWindow : public KXmlGuiWindow
+{
+ Q_OBJECT
+
+public:
+ MainWindow();
+ ~MainWindow();
+
+ static KUrl guessUrlFromString(const QString &url);
+ MainView *mainView() const;
+ WebView *currentTab() const;
+ QAction *actionByName(const QString name);
+ virtual QSize sizeHint() const;
+
+private:
+ void setupActions();
+ void setupHistoryMenu();
+ void setupToolBars();
+ void setupSidePanel();
+ SidePanel *sidePanel()
+ {
+ return m_sidePanel;
+ }
+
+public slots:
+ void slotHome();
+ void loadUrl(const KUrl &url);
+ void slotUpdateBrowser();
+
+protected:
+ bool queryClose();
+
+private slots:
+ void postLaunch();
+ void slotUpdateConfiguration();
+ void slotLoadProgress(int);
+ void slotUpdateStatusbar(const QString &string);
+ void slotUpdateActions();
+ void slotUpdateWindowTitle(const QString &title = QString());
+ void slotOpenLocation();
+ void slotAboutToShowBackMenu();
+ void geometryChangeRequested(const QRect &geometry);
+
+ // history related
+ void slotOpenActionUrl(QAction *action);
+ void slotOpenPrevious();
+ void slotOpenNext();
+
+ // File Menu slots
+ void slotFileOpen();
+ void slotFilePrintPreview();
+ void slotFilePrint();
+ void slotPrivateBrowsing(bool);
+ void slotFileSaveAs();
+ void printRequested(QWebFrame *frame);
+
+ // Edit Menu slots
+ void slotFind(const QString &);
+ void slotFindNext();
+ void slotFindPrevious();
+
+ // View Menu slots
+ void slotViewTextBigger();
+ void slotViewTextNormal();
+ void slotViewTextSmaller();
+ void slotViewPageSource();
+ void slotViewFullScreen(bool enable);
+ void slotViewFindBar();
+
+ // Tools Menu slots
+ void slotToggleInspector(bool enable);
+
+ // Settings Menu slots
+ void slotShowMenubar(bool enable);
+ void slotPreferences();
+
+private:
+ MainView *m_view;
+ FindBar *m_findBar;
+ SearchBar *m_searchBar;
+ SidePanel *m_sidePanel;
+
+ KMenu *m_historyBackMenu;
+ KMenu *m_windowMenu;
+ KActionMenu *m_historyActionMenu;
+
+ KAction *m_stopReloadAction;
+ KAction *m_stopAction;
+ KAction *m_reloadAction;
+ KAction *m_historyBackAction;
+ KAction *m_historyForwardAction;
+
+ QString m_lastSearch;
+ QString m_homePage;
+};
+
+#endif // MAINWINDOW_H
diff --git a/src/modelmenu.cpp b/src/modelmenu.cpp
new file mode 100644
index 00000000..cc43a3f3
--- /dev/null
+++ b/src/modelmenu.cpp
@@ -0,0 +1,228 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#include "modelmenu.h"
+
+
+ModelMenu::ModelMenu(QWidget * parent)
+ : KMenu(parent)
+ , m_maxRows(7)
+ , m_firstSeparator(-1)
+ , m_maxWidth(-1)
+ , m_hoverRole(0)
+ , m_separatorRole(0)
+ , m_model(0)
+{
+ connect(this, SIGNAL(aboutToShow()), this, SLOT(aboutToShow()));
+}
+
+
+bool ModelMenu::prePopulated()
+{
+ return false;
+}
+
+
+void ModelMenu::postPopulated()
+{
+}
+
+
+void ModelMenu::setModel(QAbstractItemModel *model)
+{
+ m_model = model;
+}
+
+
+QAbstractItemModel *ModelMenu::model() const
+{
+ return m_model;
+}
+
+
+void ModelMenu::setMaxRows(int max)
+{
+ m_maxRows = max;
+}
+
+
+int ModelMenu::maxRows() const
+{
+ return m_maxRows;
+}
+
+
+void ModelMenu::setFirstSeparator(int offset)
+{
+ m_firstSeparator = offset;
+}
+
+
+int ModelMenu::firstSeparator() const
+{
+ return m_firstSeparator;
+}
+
+
+void ModelMenu::setRootIndex(const QModelIndex &index)
+{
+ m_root = index;
+}
+
+
+QModelIndex ModelMenu::rootIndex() const
+{
+ return m_root;
+}
+
+
+void ModelMenu::setHoverRole(int role)
+{
+ m_hoverRole = role;
+}
+
+
+int ModelMenu::hoverRole() const
+{
+ return m_hoverRole;
+}
+
+
+void ModelMenu::setSeparatorRole(int role)
+{
+ m_separatorRole = role;
+}
+
+
+int ModelMenu::separatorRole() const
+{
+ return m_separatorRole;
+}
+
+
+Q_DECLARE_METATYPE(QModelIndex)
+void ModelMenu::aboutToShow()
+{
+ if (QMenu *menu = qobject_cast<QMenu*>(sender()))
+ {
+ QVariant v = menu->menuAction()->data();
+ if (v.canConvert<QModelIndex>())
+ {
+ QModelIndex idx = qvariant_cast<QModelIndex>(v);
+ createMenu(idx, -1, menu, menu);
+ disconnect(menu, SIGNAL(aboutToShow()), this, SLOT(aboutToShow()));
+ return;
+ }
+ }
+
+ clear();
+ if (prePopulated())
+ addSeparator();
+ int max = m_maxRows;
+ if (max != -1)
+ max += m_firstSeparator;
+ createMenu(m_root, max, this, this);
+ postPopulated();
+}
+
+void ModelMenu::createMenu(const QModelIndex &parent, int max, QMenu *parentMenu, QMenu *menu)
+{
+ if (!menu)
+ {
+ QString title = parent.data().toString();
+ menu = new QMenu(title, this);
+ QIcon icon = qvariant_cast<QIcon>(parent.data(Qt::DecorationRole));
+ menu->setIcon(icon);
+ parentMenu->addMenu(menu);
+ QVariant v;
+ v.setValue(parent);
+ menu->menuAction()->setData(v);
+ connect(menu, SIGNAL(aboutToShow()), this, SLOT(aboutToShow()));
+ return;
+ }
+
+ int end = m_model->rowCount(parent);
+ if (max != -1)
+ end = qMin(max, end);
+
+ connect(menu, SIGNAL(triggered(QAction*)), this, SLOT(triggered(QAction*)));
+ connect(menu, SIGNAL(hovered(QAction*)), this, SLOT(hovered(QAction*)));
+
+ for (int i = 0; i < end; ++i)
+ {
+ QModelIndex idx = m_model->index(i, 0, parent);
+ if (m_model->hasChildren(idx))
+ {
+ createMenu(idx, -1, menu);
+ }
+ else
+ {
+ if (m_separatorRole != 0
+ && idx.data(m_separatorRole).toBool())
+ addSeparator();
+ else
+ menu->addAction(makeAction(idx));
+ }
+ if (menu == this && i == m_firstSeparator - 1)
+ addSeparator();
+ }
+}
+
+KAction *ModelMenu::makeAction(const QModelIndex &index)
+{
+ QIcon icon = qvariant_cast<QIcon>(index.data(Qt::DecorationRole));
+ KAction *action = (KAction *) makeAction(KIcon(icon), index.data().toString(), this);
+ QVariant v;
+ v.setValue(index);
+ action->setData(v);
+ return action;
+}
+
+KAction *ModelMenu::makeAction(const KIcon &icon, const QString &text, QObject *parent)
+{
+ QFontMetrics fm(font());
+ if (-1 == m_maxWidth)
+ m_maxWidth = fm.width(QLatin1Char('m')) * 30;
+ QString smallText = fm.elidedText(text, Qt::ElideMiddle, m_maxWidth);
+ return new KAction(icon, smallText, parent);
+}
+
+void ModelMenu::triggered(QAction *action)
+{
+ QVariant v = action->data();
+ if (v.canConvert<QModelIndex>())
+ {
+ QModelIndex idx = qvariant_cast<QModelIndex>(v);
+ emit activated(idx);
+ }
+}
+
+void ModelMenu::hovered(QAction *action)
+{
+ QVariant v = action->data();
+ if (v.canConvert<QModelIndex>())
+ {
+ QModelIndex idx = qvariant_cast<QModelIndex>(v);
+ QString hoveredString = idx.data(m_hoverRole).toString();
+ if (!hoveredString.isEmpty())
+ emit hovered(hoveredString);
+ }
+}
diff --git a/src/modelmenu.h b/src/modelmenu.h
new file mode 100644
index 00000000..3cc657b3
--- /dev/null
+++ b/src/modelmenu.h
@@ -0,0 +1,92 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef MODELMENU_H
+#define MODELMENU_H
+
+// Qt Includes
+#include <QtGui>
+#include <QtCore>
+
+// KDE Includes
+#include <KIcon>
+#include <KAction>
+#include <KMenu>
+
+// A QMenu that is dynamically populated from a QAbstractItemModel
+class ModelMenu : public KMenu
+{
+ Q_OBJECT
+
+signals:
+ void activated(const QModelIndex &index);
+ void hovered(const QString &text);
+
+public:
+ ModelMenu(QWidget *parent = 0);
+
+ void setModel(QAbstractItemModel *model);
+ QAbstractItemModel *model() const;
+
+ void setMaxRows(int max);
+ int maxRows() const;
+
+ void setFirstSeparator(int offset);
+ int firstSeparator() const;
+
+ void setRootIndex(const QModelIndex &index);
+ QModelIndex rootIndex() const;
+
+ void setHoverRole(int role);
+ int hoverRole() const;
+
+ void setSeparatorRole(int role);
+ int separatorRole() const;
+
+ KAction *makeAction(const KIcon &icon, const QString &text, QObject *parent);
+
+protected:
+ // add any actions before the tree, return true if any actions are added.
+ virtual bool prePopulated();
+ // add any actions after the tree
+ virtual void postPopulated();
+ // put all of the children of parent into menu up to max
+ void createMenu(const QModelIndex &parent, int max, QMenu *parentMenu = 0, QMenu *menu = 0);
+
+private slots:
+ void aboutToShow();
+ void triggered(QAction *action);
+ void hovered(QAction *action);
+
+private:
+ KAction *makeAction(const QModelIndex &index);
+ int m_maxRows;
+ int m_firstSeparator;
+ int m_maxWidth;
+ int m_hoverRole;
+ int m_separatorRole;
+ QAbstractItemModel *m_model;
+ QPersistentModelIndex m_root;
+};
+
+#endif // MODELMENU_H
+
diff --git a/src/networkaccessmanager.cpp b/src/networkaccessmanager.cpp
new file mode 100644
index 00000000..d92edbd6
--- /dev/null
+++ b/src/networkaccessmanager.cpp
@@ -0,0 +1,165 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "networkaccessmanager.h"
+#include "networkaccessmanager.moc"
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Ui Includes
+#include "ui_password.h"
+#include "ui_proxy.h"
+
+// KDE Includes
+#include <KMessageBox>
+#include <KStandardDirs>
+
+// Qt Includes
+#include <QDialog>
+#include <QStyle>
+#include <QTextDocument>
+#include <QAuthenticator>
+#include <QNetworkProxy>
+#include <QNetworkReply>
+#include <QSslError>
+
+
+NetworkAccessManager::NetworkAccessManager(QObject *parent)
+ : QNetworkAccessManager(parent)
+{
+ connect(this, SIGNAL(authenticationRequired(QNetworkReply*, QAuthenticator*)),
+ SLOT(authenticationRequired(QNetworkReply*, QAuthenticator*)));
+ connect(this, SIGNAL(proxyAuthenticationRequired(const QNetworkProxy&, QAuthenticator*)),
+ SLOT(proxyAuthenticationRequired(const QNetworkProxy&, QAuthenticator*)));
+
+#ifndef QT_NO_OPENSSL
+ connect(this, SIGNAL(sslErrors(QNetworkReply*, const QList<QSslError>&)),
+ SLOT(sslErrors(QNetworkReply*, const QList<QSslError>&)));
+#endif
+
+ loadSettings();
+
+ QNetworkDiskCache *diskCache = new QNetworkDiskCache(this);
+ QString location = KStandardDirs::locateLocal("cache", "", true);
+ diskCache->setCacheDirectory(location);
+ setCache(diskCache);
+}
+
+
+void NetworkAccessManager::loadSettings()
+{
+ QNetworkProxy proxy;
+ if (ReKonfig::isProxyEnabled())
+ {
+ if (ReKonfig::proxyType() == 0)
+ {
+ proxy.setType(QNetworkProxy::Socks5Proxy);
+ }
+ else
+ {
+ proxy.setType(QNetworkProxy::HttpProxy);
+ }
+ proxy.setHostName(ReKonfig::proxyHostName());
+ proxy.setPort(ReKonfig::proxyPort());
+ proxy.setUser(ReKonfig::proxyUserName());
+ proxy.setPassword(ReKonfig::proxyPassword());
+ }
+ setProxy(proxy);
+}
+
+
+
+void NetworkAccessManager::authenticationRequired(QNetworkReply *reply, QAuthenticator *auth)
+{
+ MainWindow *mainWindow = Application::instance()->mainWindow();
+
+ KDialog dialog(mainWindow, Qt::Sheet);
+ dialog.setButtons(KDialog::Ok | KDialog::Cancel);
+
+ Ui::passwordWidget passwordWidget;
+ QWidget widget;
+ passwordWidget.setupUi(&widget);
+
+ dialog.setMainWidget(&widget);
+
+ passwordWidget.iconLabel->setText(QString());
+ passwordWidget.iconLabel->setPixmap(mainWindow->style()->standardIcon(QStyle::SP_MessageBoxQuestion, 0, mainWindow).pixmap(32, 32));
+
+ QString introMessage = i18n("<qt>Enter username and password for ") +
+ Qt::escape(reply->url().toString()) + i18n(" at ") + Qt::escape(reply->url().toString()) + "</qt>";
+ passwordWidget.introLabel->setText(introMessage);
+ passwordWidget.introLabel->setWordWrap(true);
+
+ if (dialog.exec() == QDialog::Accepted)
+ {
+ auth->setUser(passwordWidget.userNameLineEdit->text());
+ auth->setPassword(passwordWidget.passwordLineEdit->text());
+ }
+}
+
+void NetworkAccessManager::proxyAuthenticationRequired(const QNetworkProxy &proxy, QAuthenticator *auth)
+{
+ MainWindow *mainWindow = Application::instance()->mainWindow();
+
+ KDialog dialog(mainWindow, Qt::Sheet);
+ dialog.setButtons(KDialog::Ok | KDialog::Cancel);
+
+ Ui::proxyWidget proxyWdg;
+ QWidget widget;
+ proxyWdg.setupUi(&widget);
+
+ dialog.setMainWidget(&widget);
+
+ proxyWdg.iconLabel->setText(QString());
+ proxyWdg.iconLabel->setPixmap(mainWindow->style()->standardIcon(QStyle::SP_MessageBoxQuestion, 0, mainWindow).pixmap(32, 32));
+
+ QString introMessage = i18n("<qt>Connect to proxy ") + Qt::escape(proxy.hostName()) + i18n(" using:</qt>");
+ proxyWdg.introLabel->setText(introMessage);
+ proxyWdg.introLabel->setWordWrap(true);
+
+ if (dialog.exec() == QDialog::Accepted)
+ {
+ auth->setUser(proxyWdg.userNameLineEdit->text());
+ auth->setPassword(proxyWdg.passwordLineEdit->text());
+ }
+}
+
+#ifndef QT_NO_OPENSSL
+void NetworkAccessManager::sslErrors(QNetworkReply *reply, const QList<QSslError> &error)
+{
+ MainWindow *mainWindow = Application::instance()->mainWindow();
+
+ QStringList errorStrings;
+ for (int i = 0; i < error.count(); ++i)
+ errorStrings += error.at(i).errorString();
+ QString errors = errorStrings.join(QLatin1String("\n"));
+ int ret = KMessageBox::warningYesNo(mainWindow, i18n("SSL Errors:\n\n") + reply->url().toString() + "\n\n" + QString(errors) + "\n\n");
+ if (ret == KMessageBox::Yes)
+ reply->ignoreSslErrors();
+}
+#endif
+
diff --git a/src/networkaccessmanager.h b/src/networkaccessmanager.h
new file mode 100644
index 00000000..ebcd952d
--- /dev/null
+++ b/src/networkaccessmanager.h
@@ -0,0 +1,47 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef NETWORKACCESSMANAGER_H
+#define NETWORKACCESSMANAGER_H
+
+
+#include <QNetworkAccessManager>
+
+
+class NetworkAccessManager : public QNetworkAccessManager
+{
+ Q_OBJECT
+
+public:
+ NetworkAccessManager(QObject *parent = 0);
+
+public slots:
+ void loadSettings();
+
+private slots:
+ void authenticationRequired(QNetworkReply *reply, QAuthenticator *auth);
+ void proxyAuthenticationRequired(const QNetworkProxy &proxy, QAuthenticator *auth);
+#ifndef QT_NO_OPENSSL
+ void sslErrors(QNetworkReply *reply, const QList<QSslError> &error);
+#endif
+};
+
+#endif // NETWORKACCESSMANAGER_H
diff --git a/src/panelhistory.cpp b/src/panelhistory.cpp
new file mode 100644
index 00000000..72507663
--- /dev/null
+++ b/src/panelhistory.cpp
@@ -0,0 +1,95 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "panelhistory.h"
+#include "panelhistory.moc"
+
+// QT Includes
+#include <QLabel>
+
+// KDE Includes
+#include <KLocalizedString>
+#include <KLineEdit>
+#include <KUrl>
+
+// Local Includes
+#include "history.h"
+
+
+PanelHistory::PanelHistory(QWidget *parent)
+ : QWidget(parent)
+ , m_historyTreeView(new QTreeView)
+ , m_treeProxyModel(new TreeProxyModel(this))
+{
+ m_historyTreeView->setUniformRowHeights(true);
+ m_historyTreeView->setSelectionBehavior(QAbstractItemView::SelectRows);
+ m_historyTreeView->setTextElideMode(Qt::ElideMiddle);
+ m_historyTreeView->setAlternatingRowColors(true);
+
+ // add search bar
+ QHBoxLayout *hBoxLayout = new QHBoxLayout;
+ hBoxLayout->setContentsMargins(5, 0, 0, 0);
+ QLabel *searchLabel = new QLabel(i18n("Search: "));
+ hBoxLayout->addWidget(searchLabel);
+ KLineEdit *search = new KLineEdit;
+ hBoxLayout->addWidget(search);
+ QWidget *searchBar = new QWidget;
+ searchBar->setLayout(hBoxLayout);
+
+ // setup view
+ QVBoxLayout *vBoxLayout = new QVBoxLayout;
+ vBoxLayout->setContentsMargins(0, 0, 0, 0);
+ vBoxLayout->addWidget(searchBar);
+ vBoxLayout->addWidget(m_historyTreeView);
+ setLayout(vBoxLayout);
+
+ //-
+ HistoryManager *historyManager = Application::historyManager();
+ QAbstractItemModel *model = historyManager->historyTreeModel();
+
+ m_treeProxyModel->setSourceModel(model);
+ m_historyTreeView->setModel(m_treeProxyModel);
+ m_historyTreeView->setExpanded(m_treeProxyModel->index(0, 0), true);
+ m_historyTreeView->header()->hideSection(1);
+ QFontMetrics fm(font());
+ int header = fm.width(QLatin1Char('m')) * 40;
+ m_historyTreeView->header()->resizeSection(0, header);
+
+ connect(search, SIGNAL(textChanged(QString)), m_treeProxyModel, SLOT(setFilterFixedString(QString)));
+ connect(m_historyTreeView, SIGNAL(activated(const QModelIndex&)), this, SLOT(open()));
+}
+
+
+PanelHistory::~PanelHistory()
+{
+ delete m_treeProxyModel;
+ delete m_historyTreeView;
+}
+
+
+void PanelHistory::open()
+{
+ QModelIndex index = m_historyTreeView->currentIndex();
+ if (!index.parent().isValid())
+ return;
+ emit openUrl(index.data(HistoryModel::UrlRole).toUrl());
+}
+
diff --git a/src/panelhistory.h b/src/panelhistory.h
new file mode 100644
index 00000000..89759a84
--- /dev/null
+++ b/src/panelhistory.h
@@ -0,0 +1,55 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+#ifndef PANELHISTORY_H
+#define PANELHISTORY_H
+
+// Qt Includes
+#include <QWidget>
+
+// Local Includes
+#include "application.h"
+
+class QTreeView;
+class KUrl;
+class TreeProxyModel;
+
+
+class PanelHistory : public QWidget
+{
+ Q_OBJECT
+ Q_DISABLE_COPY(PanelHistory)
+
+public:
+ explicit PanelHistory(QWidget *parent = 0);
+ virtual ~PanelHistory();
+
+signals:
+ void openUrl(const KUrl &);
+
+private slots:
+ void open();
+
+private:
+ QTreeView *m_historyTreeView;
+ TreeProxyModel *m_treeProxyModel;
+
+};
+
+#endif // PANELHISTORY_H
diff --git a/src/password.ui b/src/password.ui
new file mode 100644
index 00000000..028e1683
--- /dev/null
+++ b/src/password.ui
@@ -0,0 +1,69 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>passwordWidget</class>
+ <widget class="QWidget" name="passwordWidget">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>343</width>
+ <height>193</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Form</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout">
+ <item row="0" column="0" colspan="2">
+ <layout class="QHBoxLayout">
+ <item>
+ <widget class="QLabel" name="iconLabel">
+ <property name="text">
+ <string>DUMMY ICON</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QLabel" name="introLabel">
+ <property name="sizePolicy">
+ <sizepolicy hsizetype="MinimumExpanding" vsizetype="MinimumExpanding">
+ <horstretch>0</horstretch>
+ <verstretch>0</verstretch>
+ </sizepolicy>
+ </property>
+ <property name="text">
+ <string>INTRO TEXT DUMMY</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>Username:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <widget class="QLineEdit" name="userNameLineEdit"/>
+ </item>
+ <item row="2" column="0">
+ <widget class="QLabel" name="lblPassword">
+ <property name="text">
+ <string>Password:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1">
+ <widget class="QLineEdit" name="passwordLineEdit">
+ <property name="echoMode">
+ <enum>QLineEdit::Password</enum>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/proxy.ui b/src/proxy.ui
new file mode 100644
index 00000000..e7440862
--- /dev/null
+++ b/src/proxy.ui
@@ -0,0 +1,62 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>proxyWidget</class>
+ <widget class="QWidget" name="proxyWidget">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>264</width>
+ <height>153</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Form</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="iconLabel">
+ <property name="text">
+ <string>ICON</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1" colspan="2">
+ <widget class="QLabel" name="introLabel">
+ <property name="text">
+ <string>Connect to proxy</string>
+ </property>
+ <property name="wordWrap">
+ <bool>true</bool>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="0" colspan="2">
+ <widget class="QLabel" name="usernameLabel">
+ <property name="text">
+ <string>Username:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="2">
+ <widget class="QLineEdit" name="userNameLineEdit"/>
+ </item>
+ <item row="2" column="0" colspan="2">
+ <widget class="QLabel" name="passwordLabel">
+ <property name="text">
+ <string>Password:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="2">
+ <widget class="QLineEdit" name="passwordLineEdit">
+ <property name="echoMode">
+ <enum>QLineEdit::Password</enum>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/rekonq.kcfg b/src/rekonq.kcfg
new file mode 100644
index 00000000..499258d2
--- /dev/null
+++ b/src/rekonq.kcfg
@@ -0,0 +1,119 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<kcfg xmlns="http://www.kde.org/standards/kcfg/1.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://www.kde.org/standards/kcfg/1.0
+ http://www.kde.org/standards/kcfg/1.0/kcfg.xsd" >
+ <kcfgfile name="rekonqrc"/>
+
+<!-- Includes -->
+<include>QtWebKit</include>
+<include>KUrl</include>
+
+<!-- General Settings -->
+ <group name="General">
+ <entry name="homePage" type="String">
+ <default>http://www.kde.org/</default>
+ </entry>
+ <entry name="downloadDir" type="Path">
+ <default>$HOME</default>
+ </entry>
+ <entry name="downloadToDefaultDir" type="Bool">
+ <default>false</default>
+ </entry>
+ <entry name="alwaysShowTabBar" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="showSideBar" type="Bool">
+ <default>false</default>
+ </entry>
+ <entry name="openTabsBack" type="Bool">
+ <default>false</default>
+ </entry>
+ </group>
+
+<!-- Fonts Settings -->
+ <group name="Fonts">
+ <entry name="standardFont" type="Font">
+ <default code="true">QFont(QWebSettings::globalSettings()->fontFamily(QWebSettings::StandardFont))</default>
+ </entry>
+ <entry name="fixedFont" type="Font">
+ <default code="true">QFont(QWebSettings::globalSettings()->fontFamily(QWebSettings::FixedFont))</default>
+ </entry>
+ <entry name="fontSize" type="Int">
+ <default>12</default>
+ </entry>
+ </group>
+
+<!-- Privacy Settings -->
+ <group name="Privacy">
+ <entry name="expireHistory" type="Int">
+ <default>1</default>
+ </entry>
+ <entry name="acceptCookies" type="Int">
+ <default>2</default>
+ </entry>
+ <entry name="keepCookiesUntil" type="Int">
+ <default>0</default>
+ </entry>
+ </group>
+
+<!-- Proxy Settings -->
+ <group name="Proxy">
+ <entry name="isProxyEnabled" type="Bool">
+ <default>false</default>
+ </entry>
+ <entry name="proxyType" type="Int">
+ <default>0</default>
+ </entry>
+ <entry name="proxyHostName" type="String">
+ </entry>
+ <entry name="proxyPort" type="Int">
+ <default>8080</default>
+ </entry>
+ <entry name="proxyUserName" type="String">
+ </entry>
+ <entry name="proxyPassword" type="Password">
+ </entry>
+ </group>
+
+<!-- WebKit Settings -->
+ <group name="Webkit">
+ <entry name="autoLoadImages" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="javascriptEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="javaEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="pluginsEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="javascriptCanOpenWindows" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="javascriptCanAccessClipboard" type="Bool">
+ <default>false</default>
+ </entry>
+ <entry name="linksIncludedInFocusChain" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="zoomTextOnly" type="Bool">
+ <default>false</default>
+ </entry>
+ <entry name="printElementBackgrounds" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="offlineStorageDatabaseEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="offlineWebApplicationCacheEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ <entry name="localStorageDatabaseEnabled" type="Bool">
+ <default>true</default>
+ </entry>
+ </group>
+
+</kcfg>
diff --git a/src/rekonq.kcfgc b/src/rekonq.kcfgc
new file mode 100644
index 00000000..50a9817d
--- /dev/null
+++ b/src/rekonq.kcfgc
@@ -0,0 +1,5 @@
+File=rekonq.kcfg
+ClassName=ReKonfig
+Singleton=true
+Mutators=true
+UseEnumTypes=true
diff --git a/src/rekonqui.rc b/src/rekonqui.rc
new file mode 100644
index 00000000..aa372538
--- /dev/null
+++ b/src/rekonqui.rc
@@ -0,0 +1,104 @@
+<?xml version="1.0"?>
+<!DOCTYPE gui SYSTEM "kpartgui.dtd">
+<gui name="rekonq" version="40">
+
+<MenuBar>
+
+<!-- ============ FILE menu =========== -->
+<Menu name="file" noMerge="1"><text>&amp;File</text>
+ <Action name="file_open" />
+ <Action name="open_location" />
+ <Separator/>
+ <Action name="new_tab" />
+ <Action name="close_tab" />
+ <Separator/>
+ <Action name="file_save_as" />
+ <Separator/>
+ <Action name="file_print_preview" />
+ <Action name="file_print" />
+ <Separator/>
+ <Action name="file_quit" />
+</Menu>
+
+<!-- ============ EDIT menu =========== -->
+<Menu name="edit" noMerge="1"><text>&amp;Edit</text>
+ <Action name="edit_undo" />
+ <Action name="edit_redo" />
+ <Separator/>
+ <Action name="edit_cut" />
+ <Action name="edit_copy" />
+ <Action name="edit_paste" />
+ <Separator/>
+ <Action name="edit_find" />
+ <Action name="edit_find_next" />
+ <Action name="edit_find_prev" />
+</Menu>
+
+<!-- ============ VIEW menu =========== -->
+<Menu name="view" noMerge="1"><text>&amp;View</text>
+ <Action name="stop_reload" />
+ <Action name="go_home" />
+ <Separator/>
+ <Action name="bigger_font" />
+ <Action name="normal_font" />
+ <Action name="smaller_font" />
+ <Separator/>
+ <Action name="page_source" />
+</Menu>
+
+<!-- ============ GO menu =========== -->
+<Menu name="go" deleted="true">
+</Menu>
+
+<!-- ============ HISTORY menu =========== -->
+<Action name="history" ><text>Hi&amp;story</text>
+</Action>
+
+<!-- ============ BOOKMARKS menu =========== -->
+<Action name="bookmarks" ><text>&amp;Bookmarks</text>
+</Action>
+
+<!-- ============ TOOLS menu =========== -->
+<Menu name="tools" noMerge="1"><text>&amp;Tools</text>
+ <Action name="web_inspector" />
+ <Action name="private_browsing" />
+</Menu>
+
+<!-- ============ SETTINGS menu =========== -->
+<Menu name="settings" noMerge="1"><text>&amp;Settings</text>
+ <Action name="options_show_menubar" />
+ <Action name="options_show_statusbar" />
+ <Merge name="StandardToolBarMenuHandler" />
+ <Merge/>
+ <Menu name="side_panels"><text>Side &amp;Panels</text>
+ <Action name="show_history_panel" />
+ </Menu>
+ <Separator/>
+ <Action name="fullscreen" />
+ <Separator/>
+ <Action name="options_configure_keybinding" />
+ <Action name="options_configure_toolbars" />
+ <Action name="options_configure" />
+</Menu>
+
+</MenuBar>
+
+<!-- ============ Main ToolBar =========== -->
+<ToolBar name="mainToolBar" position="top" iconText="iconOnly" newline="true" noMerge="1">
+<text>Main Toolbar</text>
+ <Action name="history_back" />
+ <Action name="history_forward" />
+ <Action name="stop_reload" />
+ <Action name="go_home" />
+ <Action name="new_tab" />
+ <Action name="url_bar" />
+ <Action name="search_bar" />
+</ToolBar>
+
+<!-- ============ Bookmarks ToolBar =========== -->
+<ToolBar name="bookmarksToolBar" fullWidth="true" iconText="icontextright" iconSize="16" newline="true" hidden="true" noEdit="true">
+ <text>Bookmark Toolbar</text>
+ <Action noEdit="true" name="bookmarks_bar" />
+</ToolBar>
+
+</gui>
diff --git a/src/searchbar.cpp b/src/searchbar.cpp
new file mode 100644
index 00000000..fad35748
--- /dev/null
+++ b/src/searchbar.cpp
@@ -0,0 +1,129 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "searchbar.h"
+#include "searchbar.moc"
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+
+// KDE Includes
+#include <KUrl>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+#include <QtNetwork>
+
+
+SearchBar::SearchBar(QWidget *parent) :
+ KLineEdit(parent)
+ , m_networkAccessManager(new QNetworkAccessManager(this))
+ , m_timer(new QTimer(this))
+{
+ setMinimumWidth(180);
+
+ setFocusPolicy(Qt::WheelFocus);
+ setMouseTracking(true);
+ setAcceptDrops(true);
+
+ QSizePolicy policy = sizePolicy();
+ setSizePolicy(QSizePolicy::Preferred, policy.verticalPolicy());
+
+ setClearButtonShown(true);
+
+ // better solution than using QPalette(s)..
+ setClickMessage(i18n("Search.."));
+
+ // setting QNetworkAccessManager..
+ connect(m_networkAccessManager, SIGNAL(finished(QNetworkReply*)), this, SLOT(handleNetworkData(QNetworkReply*)));
+
+ // setting QTimer..
+ m_timer->setSingleShot(true);
+ m_timer->setInterval(200);
+ connect(m_timer, SIGNAL(timeout()), SLOT(autoSuggest()));
+ connect(this, SIGNAL(textEdited(QString)), m_timer, SLOT(start()));
+
+ // connect searchNow slot..
+ connect(this, SIGNAL(returnPressed()) , this , SLOT(searchNow()));
+}
+
+
+SearchBar::~SearchBar()
+{
+}
+
+
+void SearchBar::searchNow()
+{
+ m_timer->stop();
+ QString searchText = text();
+
+ KUrl url(QLatin1String("http://www.google.com/search"));
+ url.addQueryItem(QLatin1String("q"), searchText);
+ url.addQueryItem(QLatin1String("ie"), QLatin1String("UTF-8"));
+ url.addQueryItem(QLatin1String("oe"), QLatin1String("UTF-8"));
+ url.addQueryItem(QLatin1String("client"), QLatin1String("rekonq"));
+ emit search(url);
+}
+
+
+void SearchBar::focusInEvent(QFocusEvent *event)
+{
+ KLineEdit::focusInEvent(event);
+ clear();
+}
+
+
+void SearchBar::autoSuggest()
+{
+ QString str = text();
+ QString url = QString("http://google.com/complete/search?output=toolbar&q=%1").arg(str);
+ m_networkAccessManager->get(QNetworkRequest(QString(url)));
+}
+
+
+void SearchBar::handleNetworkData(QNetworkReply *networkReply)
+{
+ QUrl url = networkReply->url();
+ if (!networkReply->error())
+ {
+ QStringList choices;
+
+ QString response(networkReply->readAll());
+ QXmlStreamReader xml(response);
+ while (!xml.atEnd())
+ {
+ xml.readNext();
+ if (xml.tokenType() == QXmlStreamReader::StartElement)
+ if (xml.name() == "suggestion")
+ {
+ QStringRef str = xml.attributes().value("data");
+ choices << str.toString();
+ }
+ }
+
+ setCompletedItems(choices, true);
+ }
+
+ networkReply->deleteLater();
+}
diff --git a/src/searchbar.h b/src/searchbar.h
new file mode 100644
index 00000000..3fdf55b4
--- /dev/null
+++ b/src/searchbar.h
@@ -0,0 +1,67 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef SEARCHBAR_H
+#define SEARCHBAR_H
+
+// KDE Includes
+#include <KLineEdit>
+
+// Forward Declarations
+class KUrl;
+class QFocusEvent;
+class QTimer;
+class QNetworkAccessManager;
+class QNetworkReply;
+
+/**
+ * This class defines an internet search bar.
+ */
+class SearchBar : public KLineEdit
+{
+ Q_OBJECT
+
+public:
+ SearchBar(QWidget *parent = 0);
+ ~SearchBar();
+
+public slots:
+ void autoSuggest();
+ void handleNetworkData(QNetworkReply *networkReply);
+
+ /**
+ * Use this slot to perform one search in one search engine
+ *
+ */
+ void searchNow();
+
+protected:
+ void focusInEvent(QFocusEvent *);
+
+signals:
+ void search(const KUrl &);
+
+private:
+ QNetworkAccessManager *m_networkAccessManager;
+ QTimer *m_timer;
+};
+
+#endif
diff --git a/src/settings.cpp b/src/settings.cpp
new file mode 100644
index 00000000..1e42413f
--- /dev/null
+++ b/src/settings.cpp
@@ -0,0 +1,212 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+// Self Includes
+#include "settings.h"
+#include "settings.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+#include "cookiejar.h"
+#include "history.h"
+#include "networkaccessmanager.h"
+#include "webview.h"
+
+//Ui Includes
+#include "ui_settings_general.h"
+#include "ui_settings_fonts.h"
+#include "ui_settings_privacy.h"
+#include "ui_settings_proxy.h"
+#include "ui_settings_webkit.h"
+
+// KDE Includes
+#include <KConfig>
+#include <KStandardDirs>
+#include <KConfigSkeleton>
+#include <KPageWidgetItem>
+#include <KFontDialog>
+#include <KUrl>
+
+// Qt Includes
+#include <QtGui>
+#include <QtWebKit>
+
+
+class Private
+{
+private:
+ Ui::general generalUi;
+ Ui::fonts fontsUi;
+ Ui::privacy privacyUi;
+ Ui::proxy proxyUi;
+ Ui::webkit webkitUi;
+
+ Private(SettingsDialog *parent);
+
+ friend class SettingsDialog;
+};
+
+
+Private::Private(SettingsDialog *parent)
+{
+ QWidget *widget;
+ KPageWidgetItem *pageItem;
+
+ widget = new QWidget;
+ generalUi.setupUi(widget);
+ widget->layout()->setMargin(0);
+ pageItem = parent->addPage(widget , i18n("General"));
+ pageItem->setIcon(KIcon("rekonq"));
+
+ widget = new QWidget;
+ fontsUi.setupUi(widget);
+ widget->layout()->setMargin(0);
+ pageItem = parent->addPage(widget , i18n("Fonts"));
+ pageItem->setIcon(KIcon("preferences-desktop-font"));
+
+ widget = new QWidget;
+ privacyUi.setupUi(widget);
+ widget->layout()->setMargin(0);
+ pageItem = parent->addPage(widget , i18n("Privacy"));
+ pageItem->setIcon(KIcon("preferences-desktop-personal"));
+
+ widget = new QWidget;
+ proxyUi.setupUi(widget);
+ widget->layout()->setMargin(0);
+ pageItem = parent->addPage(widget , i18n("Proxy"));
+ pageItem->setIcon(KIcon("preferences-system-network"));
+
+ widget = new QWidget;
+ webkitUi.setupUi(widget);
+ widget->layout()->setMargin(0);
+ pageItem = parent->addPage(widget , i18n("Webkit"));
+ QString webkitIconPath = KStandardDirs::locate("appdata", "pics/webkit-icon.png");
+ kWarning() << webkitIconPath;
+ KIcon webkitIcon = KIcon(QIcon(webkitIconPath));
+ pageItem->setIcon(webkitIcon);
+}
+
+// -----------------------------------------------------------------------------------------------------
+
+SettingsDialog::SettingsDialog(QWidget *parent)
+ : KConfigDialog(parent, "rekonfig", ReKonfig::self())
+ , d(new Private(this))
+{
+ setFaceType(KPageDialog::List);
+ showButtonSeparator(true);
+
+ setWindowTitle(i18n("rekonfig.."));
+ setModal(true);
+
+ readConfig();
+
+ connect(d->generalUi.setHomeToCurrentPageButton, SIGNAL(clicked()), this, SLOT(setHomeToCurrentPage()));
+ connect(d->privacyUi.exceptionsButton, SIGNAL(clicked()), this, SLOT(showExceptions()));
+ connect(d->privacyUi.cookiesButton, SIGNAL(clicked()), this, SLOT(showCookies()));
+
+ setWebSettingsToolTips();
+}
+
+
+
+SettingsDialog::~SettingsDialog()
+{
+ delete d;
+}
+
+
+void SettingsDialog::setWebSettingsToolTips()
+{
+ d->webkitUi.kcfg_autoLoadImages->setToolTip(i18n("Specifies whether images are automatically loaded in web pages"));
+ d->webkitUi.kcfg_javascriptEnabled->setToolTip(i18n("Enables the running of JavaScript programs."));
+ d->webkitUi.kcfg_javaEnabled->setToolTip(i18n("Enables Java applets."));
+ d->webkitUi.kcfg_pluginsEnabled->setToolTip(i18n("Enables plugins in web pages."));
+ d->webkitUi.kcfg_javascriptCanOpenWindows->setToolTip(i18n("Allows JavaScript programs to opening new windows."));
+ d->webkitUi.kcfg_javascriptCanAccessClipboard->setToolTip(i18n("Allows JavaScript programs to reading/writing to the clipboard."));
+ d->webkitUi.kcfg_linksIncludedInFocusChain->setToolTip(i18n("Includes hyperlinks in the keyboard focus chain."));
+ d->webkitUi.kcfg_zoomTextOnly->setToolTip(i18n("Applies the zoom factor on a frame to only the text or all content."));
+ d->webkitUi.kcfg_printElementBackgrounds->setToolTip(i18n("Draws also background color and images when the page is printed."));
+ d->webkitUi.kcfg_offlineStorageDatabaseEnabled->setToolTip(i18n("Support for the HTML 5 offline storage feature."));
+ d->webkitUi.kcfg_offlineWebApplicationCacheEnabled->setToolTip(i18n("Support for the HTML 5 web application cache feature."));
+ d->webkitUi.kcfg_localStorageDatabaseEnabled->setToolTip(i18n("Support for the HTML 5 local storage feature."));
+}
+
+
+// we need this function to UPDATE the config widget data..
+void SettingsDialog::readConfig()
+{
+ // ======= General
+ d->generalUi.downloadDirUrlRequester->setMode(KFile::Directory | KFile::ExistingOnly | KFile::LocalOnly);
+ d->generalUi.downloadDirUrlRequester->setUrl(ReKonfig::downloadDir());
+ connect(d->generalUi.downloadDirUrlRequester, SIGNAL(textChanged(QString)), this, SLOT(saveSettings()));
+
+ // ======= Fonts
+ d->fontsUi.kcfg_fixedFont->setOnlyFixed(true);
+
+ // ======= Proxy
+ bool proxyEnabled = ReKonfig::isProxyEnabled();
+ d->proxyUi.groupBox->setEnabled(proxyEnabled);
+ connect(d->proxyUi.kcfg_isProxyEnabled, SIGNAL(clicked(bool)), d->proxyUi.groupBox, SLOT(setEnabled(bool)));
+}
+
+
+// we need this function to SAVE settings in rc file..
+void SettingsDialog::saveSettings()
+{
+ // General
+ ReKonfig::setDownloadDir(d->generalUi.downloadDirUrlRequester->url().prettyUrl());
+
+ // Save
+ ReKonfig::self()->writeConfig();
+}
+
+
+// ----------------------------------------------------------------------------------------------
+
+
+void SettingsDialog::showCookies()
+{
+ CookiesDialog *dialog = new CookiesDialog(Application::cookieJar(), this);
+ dialog->exec();
+}
+
+
+void SettingsDialog::showExceptions()
+{
+ CookiesExceptionsDialog *dialog = new CookiesExceptionsDialog(Application::cookieJar(), this);
+ dialog->exec();
+}
+
+
+void SettingsDialog::setHomeToCurrentPage()
+{
+ MainWindow *mw = static_cast<MainWindow*>(parent());
+ WebView *webView = mw->currentTab();
+ if (webView)
+ {
+ d->generalUi.kcfg_homePage->setText(webView->url().prettyUrl());
+ }
+}
diff --git a/src/settings.h b/src/settings.h
new file mode 100644
index 00000000..26fd2d16
--- /dev/null
+++ b/src/settings.h
@@ -0,0 +1,55 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef SETTINGS_H
+#define SETTINGS_H
+
+// KDE Includes
+#include <KConfigDialog>
+
+// Forward Declarations
+class QWidget;
+class Private;
+
+
+class SettingsDialog : public KConfigDialog
+{
+ Q_OBJECT
+
+public:
+ SettingsDialog(QWidget *parent = 0);
+ ~SettingsDialog();
+
+private:
+ Private* const d;
+
+ void setWebSettingsToolTips();
+
+private slots:
+ void readConfig();
+ void saveSettings();
+
+ void setHomeToCurrentPage();
+ void showCookies();
+ void showExceptions();
+};
+
+#endif // SETTINGS_H
diff --git a/src/settings_fonts.ui b/src/settings_fonts.ui
new file mode 100644
index 00000000..de258cad
--- /dev/null
+++ b/src/settings_fonts.ui
@@ -0,0 +1,97 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>fonts</class>
+ <widget class="QWidget" name="fonts">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>414</width>
+ <height>298</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Appearance</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout_3">
+ <item>
+ <widget class="QGroupBox" name="groupBox">
+ <property name="title">
+ <string>Fonts</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <layout class="QGridLayout" name="gridLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>Standard Font</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label_2">
+ <property name="text">
+ <string>Fixed Font</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <widget class="KFontComboBox" name="kcfg_fixedFont"/>
+ </item>
+ <item row="0" column="1">
+ <widget class="KFontComboBox" name="kcfg_standardFont"/>
+ </item>
+ </layout>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QGroupBox" name="groupBox_2">
+ <property name="title">
+ <string>Dimension</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout_2">
+ <item>
+ <layout class="QHBoxLayout" name="horizontalLayout">
+ <item>
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Font Size</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QSpinBox" name="kcfg_fontSize"/>
+ </item>
+ </layout>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <spacer name="verticalSpacer">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>20</width>
+ <height>40</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>KFontComboBox</class>
+ <extends>KComboBox</extends>
+ <header>kfontcombobox.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/settings_general.ui b/src/settings_general.ui
new file mode 100644
index 00000000..44561b02
--- /dev/null
+++ b/src/settings_general.ui
@@ -0,0 +1,142 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>general</class>
+ <widget class="QWidget" name="general">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>515</width>
+ <height>415</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>General</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout_3">
+ <item>
+ <widget class="QGroupBox" name="groupBox">
+ <property name="title">
+ <string>Places</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Home Page:</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <widget class="KLineEdit" name="kcfg_homePage">
+ <property name="sizePolicy">
+ <sizepolicy hsizetype="MinimumExpanding" vsizetype="Fixed">
+ <horstretch>0</horstretch>
+ <verstretch>0</verstretch>
+ </sizepolicy>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <layout class="QHBoxLayout" name="horizontalLayout">
+ <item>
+ <widget class="QPushButton" name="setHomeToCurrentPageButton">
+ <property name="text">
+ <string>Set to current page</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <spacer name="horizontalSpacer">
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </item>
+ <item row="2" column="1">
+ <widget class="KUrlRequester" name="downloadDirUrlRequester"/>
+ </item>
+ <item row="2" column="0">
+ <widget class="QLabel" name="label_7">
+ <property name="text">
+ <string>Save downloads to:</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="1">
+ <widget class="QCheckBox" name="kcfg_downloadToDefaultDir">
+ <property name="text">
+ <string>ask where saving downloads</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QGroupBox" name="groupBox_3">
+ <property name="title">
+ <string>Tabbed Browsing</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <widget class="QCheckBox" name="kcfg_alwaysShowTabBar">
+ <property name="text">
+ <string>Always show tab bar</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QCheckBox" name="kcfg_openTabsBack">
+ <property name="text">
+ <string>Open tabs in the background</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <spacer name="verticalSpacer">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>20</width>
+ <height>40</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>KLineEdit</class>
+ <extends>QLineEdit</extends>
+ <header>klineedit.h</header>
+ </customwidget>
+ <customwidget>
+ <class>KUrlRequester</class>
+ <extends>QFrame</extends>
+ <header>kurlrequester.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/settings_privacy.ui b/src/settings_privacy.ui
new file mode 100644
index 00000000..78202688
--- /dev/null
+++ b/src/settings_privacy.ui
@@ -0,0 +1,168 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>privacy</class>
+ <widget class="QWidget" name="privacy">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>461</width>
+ <height>313</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Privacy</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <widget class="QGroupBox" name="groupBox_2">
+ <property name="title">
+ <string>History</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout_2">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label_4">
+ <property name="text">
+ <string>Remove history items:</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <widget class="QComboBox" name="kcfg_expireHistory">
+ <item>
+ <property name="text">
+ <string>After one day</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>After one week</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>After two weeks</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>After one month</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>After one year</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Manually</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QGroupBox" name="cookiesGroupBox">
+ <property name="title">
+ <string>Cookies</string>
+ </property>
+ <layout class="QGridLayout" name="_2">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label_2">
+ <property name="text">
+ <string>Accept Cookies:</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <widget class="QComboBox" name="kcfg_acceptCookies">
+ <item>
+ <property name="text">
+ <string>Always</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Never</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Only from sites you visit</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ <item row="0" column="2">
+ <widget class="QPushButton" name="exceptionsButton">
+ <property name="text">
+ <string>Exceptions...</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>Keep until:</string>
+ </property>
+ <property name="alignment">
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <widget class="QComboBox" name="kcfg_keepCookiesUntil">
+ <item>
+ <property name="text">
+ <string>They expire</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>I exit the application</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>At most 90 days</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ <item row="1" column="2">
+ <widget class="QPushButton" name="cookiesButton">
+ <property name="text">
+ <string>Cookies...</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <spacer name="verticalSpacer">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>20</width>
+ <height>136</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/settings_proxy.ui b/src/settings_proxy.ui
new file mode 100644
index 00000000..90e308a2
--- /dev/null
+++ b/src/settings_proxy.ui
@@ -0,0 +1,152 @@
+<ui version="4.0" >
+ <class>proxy</class>
+ <widget class="QWidget" name="proxy" >
+ <property name="geometry" >
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>440</width>
+ <height>223</height>
+ </rect>
+ </property>
+ <property name="windowTitle" >
+ <string>Proxy</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout" >
+ <item>
+ <widget class="QCheckBox" name="kcfg_isProxyEnabled" >
+ <property name="text" >
+ <string>Enable proxy</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QGroupBox" name="groupBox" >
+ <property name="title" >
+ <string>Proxy Settings</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout_6" >
+ <item row="1" column="0" >
+ <widget class="QLabel" name="label_9" >
+ <property name="text" >
+ <string>Type:</string>
+ </property>
+ <property name="alignment" >
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1" colspan="2" >
+ <widget class="QComboBox" name="kcfg_proxyType" >
+ <item>
+ <property name="text" >
+ <string>SOCKS 5</string>
+ </property>
+ </item>
+ <item>
+ <property name="text" >
+ <string>HTTP</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ <item row="2" column="0" >
+ <widget class="QLabel" name="label_10" >
+ <property name="text" >
+ <string>Host:</string>
+ </property>
+ <property name="alignment" >
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1" colspan="2" >
+ <widget class="KLineEdit" name="kcfg_proxyHostName" />
+ </item>
+ <item row="3" column="0" >
+ <widget class="QLabel" name="label_11" >
+ <property name="text" >
+ <string>Port:</string>
+ </property>
+ <property name="alignment" >
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="1" >
+ <widget class="QSpinBox" name="kcfg_proxyPort" >
+ <property name="maximum" >
+ <number>10000</number>
+ </property>
+ <property name="value" >
+ <number>1080</number>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="2" >
+ <spacer name="horizontalSpacer_2" >
+ <property name="orientation" >
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>293</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item row="4" column="0" >
+ <widget class="QLabel" name="label_12" >
+ <property name="text" >
+ <string>Username:</string>
+ </property>
+ <property name="alignment" >
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="4" column="1" colspan="2" >
+ <widget class="KLineEdit" name="kcfg_proxyUserName" />
+ </item>
+ <item row="5" column="0" >
+ <widget class="QLabel" name="label_13" >
+ <property name="text" >
+ <string>Password:</string>
+ </property>
+ <property name="alignment" >
+ <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
+ </property>
+ </widget>
+ </item>
+ <item row="5" column="1" colspan="2" >
+ <widget class="KLineEdit" name="kcfg_proxyPassword" />
+ </item>
+ <item row="6" column="0" >
+ <spacer name="verticalSpacer_2" >
+ <property name="orientation" >
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="sizeHint" stdset="0" >
+ <size>
+ <width>20</width>
+ <height>8</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <customwidgets>
+ <customwidget>
+ <class>KLineEdit</class>
+ <extends>QLineEdit</extends>
+ <header>klineedit.h</header>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/settings_webkit.ui b/src/settings_webkit.ui
new file mode 100644
index 00000000..362e392a
--- /dev/null
+++ b/src/settings_webkit.ui
@@ -0,0 +1,134 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>webkit</class>
+ <widget class="QWidget" name="webkit">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>564</width>
+ <height>360</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Form</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <widget class="QGroupBox" name="groupBox">
+ <property name="title">
+ <string>WebKit Settings</string>
+ </property>
+ <layout class="QGridLayout" name="gridLayout">
+ <item row="0" column="0">
+ <widget class="QCheckBox" name="kcfg_autoLoadImages">
+ <property name="text">
+ <string>Auto Load Images</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1" rowspan="6">
+ <widget class="Line" name="line">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="2">
+ <widget class="QCheckBox" name="kcfg_linksIncludedInFocusChain">
+ <property name="text">
+ <string>Links included in focus chain</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="0">
+ <widget class="QCheckBox" name="kcfg_javascriptEnabled">
+ <property name="text">
+ <string>Javascript support</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="2">
+ <widget class="QCheckBox" name="kcfg_zoomTextOnly">
+ <property name="text">
+ <string>Zoom Text Only</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="0">
+ <widget class="QCheckBox" name="kcfg_javaEnabled">
+ <property name="text">
+ <string>Java support</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="2">
+ <widget class="QCheckBox" name="kcfg_printElementBackgrounds">
+ <property name="text">
+ <string>Print element Backgrounds</string>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="0">
+ <widget class="QCheckBox" name="kcfg_pluginsEnabled">
+ <property name="text">
+ <string>Plugins</string>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="2">
+ <widget class="QCheckBox" name="kcfg_offlineStorageDatabaseEnabled">
+ <property name="text">
+ <string>Offline storage Database</string>
+ </property>
+ </widget>
+ </item>
+ <item row="4" column="0">
+ <widget class="QCheckBox" name="kcfg_javascriptCanOpenWindows">
+ <property name="text">
+ <string>Javascript can open windows</string>
+ </property>
+ </widget>
+ </item>
+ <item row="4" column="2">
+ <widget class="QCheckBox" name="kcfg_offlineWebApplicationCacheEnabled">
+ <property name="text">
+ <string>Offline Web Application Cache </string>
+ </property>
+ </widget>
+ </item>
+ <item row="5" column="0">
+ <widget class="QCheckBox" name="kcfg_javascriptCanAccessClipboard">
+ <property name="text">
+ <string>Javascript can access clipboard</string>
+ </property>
+ </widget>
+ </item>
+ <item row="5" column="2">
+ <widget class="QCheckBox" name="kcfg_localStorageDatabaseEnabled">
+ <property name="text">
+ <string>Local storage database</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <spacer name="verticalSpacer">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>20</width>
+ <height>146</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/sidepanel.cpp b/src/sidepanel.cpp
new file mode 100644
index 00000000..0fab81c0
--- /dev/null
+++ b/src/sidepanel.cpp
@@ -0,0 +1,53 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+// Self Includes
+#include "sidepanel.h"
+#include "sidepanel.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "panelhistory.h"
+
+
+SidePanel::SidePanel(const QString &title, QWidget *parent, Qt::WindowFlags flags)
+ : QDockWidget(title, parent, flags)
+ , m_panelHistory(new PanelHistory(this))
+{
+ setObjectName("sidePanel");
+ setAllowedAreas(Qt::LeftDockWidgetArea | Qt::RightDockWidgetArea);
+
+ setShown(ReKonfig::showSideBar());
+
+ connect(m_panelHistory, SIGNAL(openUrl(const KUrl&)), this, SIGNAL(openUrl(const KUrl&)));
+
+ setWidget(m_panelHistory);
+}
+
+
+SidePanel::~SidePanel()
+{
+ // Save side panel's state
+ ReKonfig::setShowSideBar(!isHidden());
+
+ delete m_panelHistory;
+}
+
diff --git a/src/sidepanel.h b/src/sidepanel.h
new file mode 100644
index 00000000..c0af7827
--- /dev/null
+++ b/src/sidepanel.h
@@ -0,0 +1,50 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef SIDEPANEL_H
+#define SIDEPANEL_H
+
+// Qt Includes
+#include <QDockWidget>
+
+// Local Includes
+#include "application.h"
+
+class KUrl;
+class PanelHistory;
+
+
+class SidePanel : public QDockWidget
+{
+ Q_OBJECT
+ Q_DISABLE_COPY(SidePanel)
+
+public:
+ explicit SidePanel(const QString &title, QWidget *parent = 0, Qt::WindowFlags flags = 0);
+ ~SidePanel();
+
+signals:
+ void openUrl(const KUrl &);
+
+private:
+ PanelHistory *m_panelHistory;
+
+};
+
+#endif // SIDEPANEL_H
diff --git a/src/stackedurlbar.cpp b/src/stackedurlbar.cpp
new file mode 100644
index 00000000..113c8769
--- /dev/null
+++ b/src/stackedurlbar.cpp
@@ -0,0 +1,152 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "stackedurlbar.h"
+#include "stackedurlbar.moc"
+
+// KDE Includes
+#include "kdebug.h"
+
+// Local Includes
+#include "application.h"
+#include "history.h"
+#include "urlbar.h"
+
+
+StackedUrlBar::StackedUrlBar(QWidget *parent)
+ : QStackedWidget(parent)
+ , m_completion(0)
+ , m_completionModel(0)
+{
+}
+
+
+StackedUrlBar::~StackedUrlBar()
+{
+ delete m_completion;
+ delete m_completionModel;
+}
+
+
+UrlBar *StackedUrlBar::currentUrlBar()
+{
+ return urlBar(currentIndex());
+}
+
+
+UrlBar *StackedUrlBar::urlBar(int index)
+{
+ UrlBar *urlBar = qobject_cast<UrlBar*>(QStackedWidget::widget(index));
+ if (!urlBar)
+ {
+ kWarning() << "URL bar with index" << index << "not found. Returning NULL. line:" << __LINE__;
+ }
+
+ return urlBar;
+}
+
+
+void StackedUrlBar::addUrlBar(UrlBar* urlBar)
+{
+ QStackedWidget::addWidget(urlBar);
+
+ // setup completion objects
+ urlBar->setCompletionObject(completion());
+}
+
+
+void StackedUrlBar::setCurrentUrlBar(UrlBar* urlBar)
+{
+ QStackedWidget::setCurrentWidget(urlBar);
+}
+
+
+void StackedUrlBar::removeUrlBar(UrlBar* urlBar)
+{
+ QStackedWidget::removeWidget(urlBar);
+}
+
+
+void StackedUrlBar::clear()
+{
+ currentUrlBar()->clearHistory();
+
+ for (int i = 0; i < count(); ++i)
+ {
+ urlBar(i)->clear();
+ }
+}
+
+
+QList<const UrlBar* > StackedUrlBar::urlBars()
+{
+ QList<const UrlBar *> list;
+ for (int i = 0; i < count(); ++i)
+ {
+ const UrlBar* u = urlBar(i);
+ list.append(u);
+ }
+ return list;
+}
+
+
+KCompletion *StackedUrlBar::completion()
+{
+ // make sure completion was created
+ if (!m_completion)
+ {
+ m_completion = new KCompletion();
+ m_completion->setCompletionMode(KGlobalSettings::CompletionPopupAuto);
+ m_completion->setOrder(KCompletion::Weighted);
+ m_completion->setIgnoreCase(true);
+
+ kDebug() << "Initialize completion list...";
+
+ HistoryCompletionModel *model = completionModel();
+ int count = model->rowCount();
+
+ kDebug() << "...initialize history items" << count;
+
+ // change order to insertion to avoid confusion of the addItem method
+ // in weighted it expects format string:number and it thinks http it the whole string
+ m_completion->setOrder(KCompletion::Insertion);
+ for (int i = 0; i < count; ++i)
+ {
+ QString item = model->data(model->index(i, 0)).toString();
+ item.remove(QRegExp("^http://|/$"));
+ m_completion->addItem(item);
+ }
+ m_completion->setOrder(KCompletion::Weighted);
+ }
+
+ return m_completion;
+}
+
+
+HistoryCompletionModel *StackedUrlBar::completionModel()
+{
+ if (!m_completionModel)
+ {
+ m_completionModel = new HistoryCompletionModel(this);
+ m_completionModel->setSourceModel(Application::historyManager()->historyFilterModel());
+ }
+ return m_completionModel;
+}
diff --git a/src/stackedurlbar.h b/src/stackedurlbar.h
new file mode 100644
index 00000000..d3aea16f
--- /dev/null
+++ b/src/stackedurlbar.h
@@ -0,0 +1,64 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+
+#ifndef STACKEDURLBAR_H
+#define STACKEDURLBAR_H
+
+// Qt Includes
+#include <QStackedWidget>
+
+class KCompletion;
+class HistoryCompletionModel;
+class UrlBar;
+
+class StackedUrlBar : public QStackedWidget
+{
+ Q_OBJECT
+
+public:
+ StackedUrlBar(QWidget *parent = 0);
+ ~StackedUrlBar();
+
+public:
+ UrlBar *currentUrlBar();
+ UrlBar *urlBar(int index);
+ void addUrlBar(UrlBar *urlBar);
+ void setCurrentUrlBar(UrlBar *urlBar);
+ void removeUrlBar(UrlBar *urlBar);
+
+ QList<const UrlBar *> urlBars();
+
+ KCompletion *completion();
+ HistoryCompletionModel *completionModel();
+
+public slots:
+ void clear();
+
+private:
+ Q_DISABLE_COPY(StackedUrlBar)
+
+ KCompletion *m_completion;
+ HistoryCompletionModel *m_completionModel;
+};
+
+#endif // STACKEDURLBAR_H
+
diff --git a/src/tabbar.cpp b/src/tabbar.cpp
new file mode 100644
index 00000000..be1b05fd
--- /dev/null
+++ b/src/tabbar.cpp
@@ -0,0 +1,145 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+//Self Includes
+#include "tabbar.h"
+#include "tabbar.moc"
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+#include "history.h"
+#include "urlbar.h"
+#include "webview.h"
+
+// KDE Includes
+#include <KShortcut>
+#include <KStandardShortcut>
+#include <KMessageBox>
+#include <KAction>
+#include <KDebug>
+#include <KGlobalSettings>
+
+// Qt Includes
+#include <QtGui>
+
+
+TabBar::TabBar(QWidget *parent)
+ : KTabBar(parent)
+ , m_parent(parent)
+{
+ setElideMode(Qt::ElideRight);
+ setContextMenuPolicy(Qt::CustomContextMenu);
+ setMovable(true);
+ connect(this, SIGNAL(customContextMenuRequested(const QPoint &)), this,
+ SLOT(contextMenuRequested(const QPoint &)));
+
+ // tabbar font
+ QFont standardFont = KGlobalSettings::generalFont();
+ QString fontFamily = standardFont.family();
+ int dim = standardFont.pointSize();
+ setFont(QFont(fontFamily, dim - 1));
+}
+
+
+TabBar::~TabBar()
+{
+}
+
+
+QSize TabBar::tabSizeHint(int index) const
+{
+ QSize s = m_parent->sizeHint();
+ int w;
+
+ int n = count();
+
+ if (n > 6)
+ {
+ w = s.width() / 5;
+ }
+ else
+ {
+ if (n > 3)
+ {
+ w = s.width() / 4;
+ }
+ else
+ {
+ w = s.width() / 3;
+ }
+ }
+ int h = KTabBar::tabSizeHint(index).height();
+
+ QSize ts = QSize(w, h);
+ return ts;
+}
+
+
+void TabBar::contextMenuRequested(const QPoint &position)
+{
+ KMenu menu;
+ MainWindow *mainWindow = Application::instance()->mainWindow();
+
+ menu.addAction(mainWindow->actionByName(QLatin1String("new_tab")));
+ int index = tabAt(position);
+ if (-1 != index)
+ {
+ m_actualIndex = index;
+
+ menu.addAction(KIcon("tab-duplicate"), i18n("Clone Tab"), this, SLOT(cloneTab()));
+ menu.addSeparator();
+ menu.addAction(KIcon("tab-close"), i18n("&Close Tab"), this, SLOT(closeTab()));
+ menu.addAction(KIcon("tab-close-other"), i18n("Close &Other Tabs"), this, SLOT(closeOtherTabs()));
+ menu.addSeparator();
+ menu.addAction(KIcon("view-refresh"), i18n("Reload Tab"), this, SLOT(reloadTab()));
+ }
+ else
+ {
+ menu.addSeparator();
+ }
+ menu.addAction(i18n("Reload All Tabs"), this, SIGNAL(reloadAllTabs()));
+ menu.exec(QCursor::pos());
+}
+
+
+void TabBar::cloneTab()
+{
+ emit cloneTab(m_actualIndex);
+}
+
+
+void TabBar::closeTab()
+{
+ emit closeTab(m_actualIndex);
+}
+
+
+void TabBar::closeOtherTabs()
+{
+ emit closeOtherTabs(m_actualIndex);
+}
+
+
+void TabBar::reloadTab()
+{
+ emit reloadTab(m_actualIndex);
+}
diff --git a/src/tabbar.h b/src/tabbar.h
new file mode 100644
index 00000000..8563793f
--- /dev/null
+++ b/src/tabbar.h
@@ -0,0 +1,78 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef TABBAR_H
+#define TABBAR_H
+
+// KDE Includes
+#include <KTabBar>
+
+// Qt Includes
+#include <QShortcut>
+
+/**
+ * Tab bar with a few more features such as
+ * a context menu and shortcuts
+ *
+ */
+
+class TabBar : public KTabBar
+{
+ Q_OBJECT
+
+
+public:
+ TabBar(QWidget *parent = 0);
+ ~TabBar();
+
+signals:
+ void cloneTab(int index);
+ void closeTab(int index);
+ void closeOtherTabs(int index);
+ void reloadTab(int index);
+ void reloadAllTabs();
+
+protected:
+ /**
+ * Added to fix tab dimension
+ */
+ virtual QSize tabSizeHint(int index) const;
+
+private slots:
+ void cloneTab();
+ void closeTab();
+ void closeOtherTabs();
+ void reloadTab();
+ void contextMenuRequested(const QPoint &position);
+
+private:
+ friend class MainView;
+
+ QWidget *m_parent;
+
+ /**
+ * the index in which we are seeing a Context menu
+ */
+ int m_actualIndex;
+};
+
+#endif
diff --git a/src/urlbar.cpp b/src/urlbar.cpp
new file mode 100644
index 00000000..29eaed70
--- /dev/null
+++ b/src/urlbar.cpp
@@ -0,0 +1,240 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "urlbar.h"
+#include "urlbar.moc"
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+
+// KDE Includes
+#include <KDebug>
+#include <KCompletionBox>
+#include <KUrl>
+
+// Local Includes
+#include "application.h"
+#include "history.h"
+#include "lineedit.h"
+#include "mainwindow.h"
+#include "webview.h"
+
+
+QColor UrlBar::s_defaultBaseColor;
+
+UrlBar::UrlBar(QWidget *parent)
+ : KHistoryComboBox(true, parent)
+ , m_lineEdit(new LineEdit)
+ , m_progress(0)
+{
+ setUrlDropsEnabled(true);
+ setAutoDeleteCompletionObject(true);
+ setMinimumWidth(180);
+
+ setTrapReturnKey(true);
+
+ setupLineEdit();
+
+ // add every item to history
+ connect(this, SIGNAL(returnPressed(const QString&)), SLOT(slotActivated(const QString&)));
+ connect(completionBox(), SIGNAL(activated(const QString&)), SLOT(slotActivated(const QString&)));
+
+ connect(this, SIGNAL(cleared()), SLOT(slotCleared()));
+
+ // setup completion box
+ completionBox()->setTabHandling(true); // Konqueror bug #167135
+
+ // set dropdown list background
+ QPalette p = view()->palette();
+ p.setColor(QPalette::Base, palette().color(QPalette::Base));
+ view()->setPalette(p);
+
+ // set empty item with default icon
+ slotUpdateUrl();
+}
+
+
+UrlBar::~UrlBar()
+{
+}
+
+
+void UrlBar::setupLineEdit()
+{
+ // Make m_lineEdit background transparent
+ QPalette p = m_lineEdit->palette();
+ p.setColor(QPalette::Base, Qt::transparent);
+ m_lineEdit->setPalette(p);
+
+ if (!s_defaultBaseColor.isValid())
+ {
+ s_defaultBaseColor = palette().color(QPalette::Base);
+ }
+
+ setLineEdit(m_lineEdit);
+
+ // Make the lineedit consume the Qt::Key_Enter event...
+ lineEdit()->setTrapReturnKey(true);
+
+ lineEdit()->setHandleSignals(true);
+
+ // clear the URL bar
+ lineEdit()->clear();
+}
+
+
+void UrlBar::setUrl(const QUrl& url)
+{
+ if (url.isEmpty())
+ return;
+
+ m_currentUrl = url;
+ slotUpdateUrl();
+}
+
+
+void UrlBar::slotUpdateUrl()
+{
+ if (count())
+ {
+ changeUrl(0, Application::instance()->icon(m_currentUrl), m_currentUrl);
+ }
+ else
+ {
+ insertUrl(0, Application::instance()->icon(m_currentUrl), m_currentUrl);
+ }
+
+ setCurrentIndex(0);
+
+ // important security consideration: always display the beginning
+ // of the url rather than its end to prevent spoofing attempts.
+ // Must be AFTER setCurrentIndex
+ if (!hasFocus())
+ {
+ lineEdit()->setCursorPosition(0);
+ }
+}
+
+
+inline void UrlBar::slotActivated(const QString& url)
+{
+ if (url.isEmpty())
+ return;
+
+ setUrl(url);
+
+ Application::historyManager()->addHistoryEntry(url);
+
+ emit activated(m_currentUrl);
+}
+
+
+inline void UrlBar::slotCleared()
+{
+ // clear the history on user's request from context menu
+ clear();
+ Application::historyManager()->clear();
+}
+
+
+inline void UrlBar::slotLoadFinished(bool)
+{
+ // reset progress bar after small delay
+ m_progress = 0;
+ QTimer::singleShot(200, this, SLOT(repaint()));
+}
+
+
+inline void UrlBar::slotUpdateProgress(int progress)
+{
+ m_progress = progress;
+ repaint();
+}
+
+
+void UrlBar::paintEvent(QPaintEvent *event)
+{
+ // set background color of UrlBar
+ QPalette p = palette();
+ p.setColor(QPalette::Base, s_defaultBaseColor);
+ setPalette(p);
+
+ KHistoryComboBox::paintEvent(event);
+
+ if (!hasFocus())
+ {
+ QPainter painter(this);
+
+ QColor loadingColor;
+ if (m_currentUrl.scheme() == QLatin1String("https"))
+ {
+ loadingColor = QColor(248, 248, 100);
+ }
+ else
+ {
+ loadingColor = QColor(116, 192, 250);
+ }
+ painter.setBrush(generateGradient(loadingColor, height()));
+ painter.setPen(Qt::transparent);
+
+ QRect backgroundRect = lineEdit()->frameGeometry();
+ int mid = backgroundRect.width() / 100 * m_progress;
+ QRect progressRect(backgroundRect.x(), backgroundRect.y(), mid, backgroundRect.height());
+ painter.drawRect(progressRect);
+ painter.end();
+ }
+}
+
+
+void UrlBar::focusOutEvent(QFocusEvent *event)
+{
+ // set back last loaded url in case user cleared it
+ setUrl(m_currentUrl);
+
+ KHistoryComboBox::focusOutEvent(event);
+}
+
+
+QSize UrlBar::sizeHint() const
+{
+ QSize size(lineEdit()->sizeHint());
+ // make it (more or less) the same height with search bar (at least on oxygen)
+// size.setHeight(size.height() + 2);
+ return size;
+}
+
+QLinearGradient UrlBar::generateGradient(const QColor &color, int height)
+{
+ QColor base = s_defaultBaseColor;
+ base.setAlpha(0);
+ QColor barColor = color;
+ barColor.setAlpha(200);
+ QLinearGradient gradient(0, 0, 0, height);
+ gradient.setColorAt(0, base);
+ gradient.setColorAt(0.25, barColor.lighter(120));
+ gradient.setColorAt(0.5, barColor);
+ gradient.setColorAt(0.75, barColor.lighter(120));
+ gradient.setColorAt(1, base);
+ return gradient;
+}
diff --git a/src/urlbar.h b/src/urlbar.h
new file mode 100644
index 00000000..236792bd
--- /dev/null
+++ b/src/urlbar.h
@@ -0,0 +1,99 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef URLBAR_H
+#define URLBAR_H
+
+// Qt Includes
+#include <QIcon>
+#include <QPointer>
+#include <QUrl>
+
+// KDE Includes
+#include <KUrl>
+#include <KHistoryComboBox>
+
+// Local Includes
+#include "lineedit.h"
+
+
+// Forward Declarations
+class QLinearGradient;
+class QWidget;
+
+
+class UrlBar : public KHistoryComboBox
+{
+ Q_OBJECT
+
+public:
+ UrlBar(QWidget *parent = 0);
+ ~UrlBar();
+
+ void selectAll() const
+ {
+ lineEdit()->selectAll();
+ }
+ KUrl url() const
+ {
+ return m_currentUrl;
+ }
+
+ QSize sizeHint() const;
+
+signals:
+ void activated(const KUrl&);
+
+public slots:
+ void setUrl(const QUrl &url);
+ void slotUpdateProgress(int progress);
+
+private slots:
+ void slotActivated(const QString&);
+ void slotLoadFinished(bool);
+ void slotCleared();
+ void slotUpdateUrl();
+
+protected:
+ virtual void paintEvent(QPaintEvent *event);
+ virtual void focusOutEvent(QFocusEvent *event);
+
+private:
+ void setupLineEdit();
+
+ KLineEdit *lineEdit() const
+ {
+ return m_lineEdit;
+ }
+
+ static QLinearGradient generateGradient(const QColor &color, int height);
+
+ static QColor s_defaultBaseColor;
+
+ LineEdit *m_lineEdit;
+
+ QIcon m_currentIcon;
+ KUrl m_currentUrl;
+ int m_progress;
+};
+
+#endif
diff --git a/src/webview.cpp b/src/webview.cpp
new file mode 100644
index 00000000..5f42112b
--- /dev/null
+++ b/src/webview.cpp
@@ -0,0 +1,504 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008 Benjamin C. Meyer <ben@meyerhome.net>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+// Self Includes
+#include "webview.h"
+#include "webview.moc"
+
+// Auto Includes
+#include "rekonq.h"
+
+// Local Includes
+#include "application.h"
+#include "mainwindow.h"
+#include "mainview.h"
+#include "cookiejar.h"
+#include "networkaccessmanager.h"
+#include "download.h"
+#include "history.h"
+
+
+// KDE Includes
+#include <KStandardDirs>
+#include <KUrl>
+#include <KActionCollection>
+#include <KDebug>
+#include <KToolInvocation>
+
+// Qt Includes
+#include <QtCore>
+#include <QtGui>
+#include <QtWebKit>
+#include <QUiLoader>
+
+
+WebPage::WebPage(QObject *parent)
+ : QWebPage(parent)
+ , m_keyboardModifiers(Qt::NoModifier)
+ , m_pressedButtons(Qt::NoButton)
+ , m_openInNewTab(false)
+{
+ setNetworkAccessManager(Application::networkAccessManager());
+
+ setForwardUnsupportedContent(true);
+ connect(this, SIGNAL(unsupportedContent(QNetworkReply *)), this, SLOT(handleUnsupportedContent(QNetworkReply *)));
+}
+
+
+WebPage::~WebPage()
+{
+}
+
+
+bool WebPage::acceptNavigationRequest(QWebFrame *frame, const QNetworkRequest &request, NavigationType type)
+{
+ QString scheme = request.url().scheme();
+ if (scheme == QLatin1String("mailto"))
+ {
+ KToolInvocation::invokeMailer(request.url());
+ return false;
+ }
+
+ WebView *webView;
+
+ switch (type)
+ {
+
+ // user clicked on a link or pressed return on a focused link.
+ case QWebPage::NavigationTypeLinkClicked:
+
+ if (m_keyboardModifiers & Qt::ControlModifier || m_pressedButtons == Qt::MidButton)
+ {
+ webView = Application::instance()->newWebView();
+ webView->setFocus();
+ webView->load(request);
+ m_keyboardModifiers = Qt::NoModifier;
+ m_pressedButtons = Qt::NoButton;
+ return false;
+ }
+
+ if (frame == mainFrame())
+ {
+ m_loadingUrl = request.url();
+ emit loadingUrl(m_loadingUrl);
+ }
+ else
+ {
+ // if frame doesn't exists (perhaps) we are pointing to a blank target..
+ if (!frame)
+ {
+ webView = Application::instance()->newWebView();
+ webView->setFocus();
+ webView->load(request);
+ return false;
+ }
+ }
+ break;
+
+ // user activated a submit button for an HTML form.
+ case QWebPage::NavigationTypeFormSubmitted:
+ break;
+
+ // Navigation to a previously shown document in the back or forward history is requested.
+ case QWebPage::NavigationTypeBackOrForward:
+ break;
+
+ // user activated the reload action.
+ case QWebPage::NavigationTypeReload:
+
+#if QT_VERSION <= 040500
+ // HACK Ported from Arora
+ // A short term hack until QtWebKit can get a reload without cache QAction
+ // *FYI* currently type is never NavigationTypeReload
+ // See: https://bugs.webkit.org/show_bug.cgi?id=24283
+ if (qApp->keyboardModifiers() & Qt::ShiftModifier)
+ {
+ QNetworkRequest newRequest(request);
+ newRequest.setAttribute(QNetworkRequest::CacheLoadControlAttribute,
+ QNetworkRequest::AlwaysNetwork);
+ mainFrame()->load(request);
+ return false;
+ }
+#endif
+
+ break;
+
+ // An HTML form was submitted a second time.
+ case QWebPage::NavigationTypeFormResubmitted:
+ break;
+
+ // A navigation to another document using a method not listed above.
+ case QWebPage::NavigationTypeOther:
+ break;
+
+ // should be nothing..
+ default:
+ break;
+ }
+
+ return QWebPage::acceptNavigationRequest(frame, request, type);
+}
+
+
+QWebPage *WebPage::createWindow(QWebPage::WebWindowType type)
+{
+ // added to manage web modal dialogs
+ if (type == QWebPage::WebModalDialog)
+ {
+ // FIXME : need a "real" implementation..
+ kWarning() << "Modal Dialog ---------------------------------------";
+ QWebView *w = new QWebView();
+ w->show();
+ return w->page();
+ }
+
+ if (m_keyboardModifiers & Qt::ControlModifier || m_pressedButtons == Qt::MidButton)
+ {
+ m_openInNewTab = true;
+ }
+
+ if (m_openInNewTab)
+ {
+ m_openInNewTab = false;
+ return Application::instance()->newWebView()->page();
+ }
+
+ MainWindow *mainWindow = Application::instance()->mainWindow();
+ return mainWindow->currentTab()->page();
+}
+
+
+QObject *WebPage::createPlugin(const QString &classId, const QUrl &url, const QStringList &paramNames, const QStringList &paramValues)
+{
+ kWarning() << "creating PLUGIN for rekonq ";
+ kWarning() << "classId = " << classId;
+ kWarning() << "url = " << url;
+ kWarning() << "Param Names = " << paramNames;
+ kWarning() << "Param Values = " << paramValues;
+
+ QUiLoader loader;
+ return loader.createWidget(classId, view());
+}
+
+
+void WebPage::handleUnsupportedContent(QNetworkReply *reply)
+{
+ // create convenience fake api:// protocol for KDE apidox search and Qt docs
+ if (reply->url().scheme() == "api")
+ {
+ QString path;
+ QString className = reply->url().host().toLower();
+ if (className[0] == 'k')
+ {
+ path = QString("http://api.kde.org/new.classmapper.php?class=%1").arg(className);
+ }
+ else if (className[0] == 'q')
+ {
+ path = QString("http://doc.trolltech.com/4.5/%1.html").arg(className);
+ }
+ QUrl url(path);
+
+ Application::instance()->mainWindow()->loadUrl(url);
+ return;
+ }
+
+ if (reply->error() == QNetworkReply::NoError)
+ {
+ // st iframe unwanted download fix
+ if (reply->header(QNetworkRequest::ContentTypeHeader).isValid())
+ {
+ KUrl srcUrl = reply->url();
+ Application::downloadManager()->newDownload(srcUrl);
+ }
+ return;
+ }
+
+ // display "not found" page
+ QString notfoundFilePath = KStandardDirs::locate("data", "rekonq/htmls/notfound.html");
+ QFile file(notfoundFilePath);
+ bool isOpened = file.open(QIODevice::ReadOnly);
+ if (!isOpened)
+ {
+ kWarning() << "Couldn't open the notfound.html file";
+ return;
+ }
+ QString title = i18n("Error loading page: ") + reply->url().toString();
+
+ QString imagePath = KIconLoader::global()->iconPath("rekonq", KIconLoader::NoGroup, false);
+
+ QString html = QString(QLatin1String(file.readAll()))
+ .arg(title)
+ .arg("file://" + imagePath)
+ .arg(reply->errorString())
+ .arg(reply->url().toString());
+
+ QList<QWebFrame*> frames;
+ frames.append(mainFrame());
+ while (!frames.isEmpty())
+ {
+ QWebFrame *firstFrame = frames.takeFirst();
+ if (firstFrame->url() == reply->url())
+ {
+ firstFrame->setHtml(html, reply->url());
+ return;
+ }
+ QList<QWebFrame *> children = firstFrame->childFrames();
+ foreach(QWebFrame *frame, children)
+ {
+ frames.append(frame);
+ }
+ }
+ if (m_loadingUrl == reply->url())
+ {
+ mainFrame()->setHtml(html, reply->url());
+ // Don't put error pages to the history.
+ Application::historyManager()->removeHistoryEntry(reply->url(), mainFrame()->title());
+ }
+}
+
+
+// -----------------------------------------------------------------------------------------------------------------
+
+
+KActionCollection* WebView::s_webActionCollection;
+
+
+WebView::WebView(QWidget* parent)
+ : QWebView(parent)
+ , m_page(new WebPage(this))
+ , m_progress(0)
+{
+ setPage(m_page);
+ connect(page(), SIGNAL(statusBarMessage(const QString&)), this, SLOT(setStatusBarText(const QString&)));
+ connect(this, SIGNAL(loadProgress(int)), this, SLOT(setProgress(int)));
+ connect(this, SIGNAL(loadFinished(bool)), this, SLOT(loadFinished()));
+ connect(page(), SIGNAL(loadingUrl(const QUrl&)), this, SIGNAL(urlChanged(const QUrl &)));
+ connect(page(), SIGNAL(downloadRequested(const QNetworkRequest &)), this, SLOT(downloadRequested(const QNetworkRequest &)));
+ page()->setForwardUnsupportedContent(true);
+}
+
+
+KActionCollection* WebView::webActions()
+{
+ if (!s_webActionCollection)
+ {
+ s_webActionCollection = new KActionCollection(this);
+
+ QAction *a;
+
+ a = new KAction(KIcon("tab-new"), i18n("Open Link in New &Tab"), this);
+ connect(a, SIGNAL(triggered()), this, SLOT(openLinkInNewTab()));
+ s_webActionCollection->addAction(QLatin1String("open_link_in_new_tab"), a);
+
+ a = pageAction(QWebPage::Cut);
+ a->setIcon(KIcon("edit-cut"));
+ a->setText(i18n("Cu&t"));
+ s_webActionCollection->addAction(QLatin1String("edit_cut"), a);
+
+ a = pageAction(QWebPage::Copy);
+ a->setIcon(KIcon("edit-copy"));
+ a->setText(i18n("&Copy"));
+ s_webActionCollection->addAction(QLatin1String("edit_copy"), a);
+
+ a = pageAction(QWebPage::Paste);
+ a->setIcon(KIcon("edit-paste"));
+ a->setText(i18n("&Paste"));
+ s_webActionCollection->addAction(QLatin1String("edit_paste"), a);
+
+ a = pageAction(QWebPage::DownloadImageToDisk);
+ a->setIcon(KIcon("folder-image"));
+ a->setText(i18n("&Save Image As..."));
+ s_webActionCollection->addAction(QLatin1String("save_image_as"), a);
+
+ a = pageAction(QWebPage::CopyImageToClipboard);
+ a->setIcon(KIcon("insert-image"));
+ a->setText(i18n("&Copy This Image"));
+ s_webActionCollection->addAction(QLatin1String("copy_this_image"), a);
+
+ a = pageAction(QWebPage::DownloadLinkToDisk);
+ a->setIcon(KIcon("folder-downloads"));
+ a->setText(i18n("&Save Link As..."));
+ s_webActionCollection->addAction(QLatin1String("save_link_as"), a);
+
+ a = pageAction(QWebPage::CopyLinkToClipboard);
+ a->setIcon(KIcon("insert-link"));
+ a->setText(i18n("&Copy Link Location"));
+ s_webActionCollection->addAction(QLatin1String("copy_link_location"), a);
+
+ a = pageAction(QWebPage::InspectElement);
+ a->setIcon(KIcon("tools-report-bug"));
+ a->setText(i18n("&Inspect Element"));
+ s_webActionCollection->addAction(QLatin1String("inspect_element"), a);
+ }
+
+ return s_webActionCollection;
+}
+
+
+void WebView::contextMenuEvent(QContextMenuEvent *event)
+{
+ QWebHitTestResult result = page()->mainFrame()->hitTestContent(event->pos());
+ MainWindow *mainwindow = Application::instance()->mainWindow();
+
+ QAction *addBookmarkAction = Application::bookmarkProvider()->actionByName("add_bookmark_payload");
+ addBookmarkAction->setText(i18n("Bookmark This Page"));
+ addBookmarkAction->setData(QVariant());
+ KMenu menu(this);
+
+ bool linkIsEmpty = result.linkUrl().isEmpty();
+ if (!linkIsEmpty)
+ {
+ menu.addAction(webActions()->action("open_link_in_new_tab"));
+ }
+ else
+ {
+ menu.addAction(mainwindow->actionByName("new_tab"));
+ }
+ menu.addAction(mainwindow->actionByName("view_redisplay"));
+ menu.addSeparator();
+
+ if (page()->settings()->testAttribute(QWebSettings::DeveloperExtrasEnabled))
+ {
+ menu.addAction(webActions()->action("inspect_element"));
+ menu.addSeparator();
+ }
+
+ menu.addAction(mainwindow->actionByName("history_back"));
+ menu.addAction(mainwindow->actionByName("history_forward"));
+ menu.addSeparator();
+
+ if (result.isContentSelected() && result.isContentEditable())
+ {
+ menu.addAction(webActions()->action("edit_cut"));
+ }
+
+ if (result.isContentSelected())
+ {
+ menu.addAction(webActions()->action("edit_copy"));
+ }
+
+ if (result.isContentEditable())
+ {
+ menu.addAction(webActions()->action("edit_paste"));
+ }
+
+ if (!linkIsEmpty)
+ {
+ menu.addSeparator();
+ if (!result.pixmap().isNull())
+ {
+ // TODO Add "View Image"
+ menu.addAction(webActions()->action("save_image_as"));
+ menu.addAction(webActions()->action("copy_this_image"));
+ }
+ menu.addAction(webActions()->action("save_link_as"));
+ menu.addAction(webActions()->action("copy_link_location"));
+ addBookmarkAction->setData(result.linkUrl());
+ addBookmarkAction->setText(i18n("&Bookmark This Link"));
+ }
+ menu.addSeparator();
+
+ menu.addAction(addBookmarkAction);
+ menu.exec(mapToGlobal(event->pos()));
+}
+
+
+void WebView::wheelEvent(QWheelEvent *event)
+{
+ if (QApplication::keyboardModifiers() & Qt::ControlModifier)
+ {
+ int numDegrees = event->delta() / 8;
+ int numSteps = numDegrees / 15;
+ setTextSizeMultiplier(textSizeMultiplier() + numSteps * 0.1);
+ event->accept();
+ return;
+ }
+ QWebView::wheelEvent(event);
+}
+
+
+void WebView::openLinkInNewTab()
+{
+ m_page->m_openInNewTab = true;
+ pageAction(QWebPage::OpenLinkInNewWindow)->trigger();
+}
+
+
+void WebView::loadFinished()
+{
+ if (m_progress != 100)
+ {
+ kWarning() << "Recieved finished signal while progress is still:" << progress()
+ << "Url:" << url();
+ }
+ m_progress = 0;
+}
+
+
+void WebView::mousePressEvent(QMouseEvent *event)
+{
+ m_page->m_pressedButtons = event->buttons();
+ m_page->m_keyboardModifiers = event->modifiers();
+ QWebView::mousePressEvent(event);
+}
+
+
+void WebView::mouseReleaseEvent(QMouseEvent *event)
+{
+ QWebView::mouseReleaseEvent(event);
+ if (!event->isAccepted() && (m_page->m_pressedButtons & Qt::MidButton))
+ {
+ KUrl url(QApplication::clipboard()->text(QClipboard::Selection));
+ if (!url.isEmpty() && url.isValid() && !url.scheme().isEmpty())
+ {
+ setUrl(url);
+ }
+ }
+}
+
+
+void WebView::downloadRequested(const QNetworkRequest &request)
+{
+ KUrl srcUrl = request.url();
+ QString path = ReKonfig::downloadDir() + QString("/") + srcUrl.fileName();
+ KUrl destUrl = KUrl(path);
+ Application::downloadManager()->newDownload(srcUrl);
+}
+
+
+void WebView::keyPressEvent(QKeyEvent *event)
+{
+ if ((event->modifiers() == Qt::ControlModifier) && (event->key() == Qt::Key_Tab))
+ {
+ emit ctrlTabPressed();
+ return;
+ }
+
+ if ((event->modifiers() == Qt::ControlModifier + Qt::ShiftModifier) && (event->key() == Qt::Key_Backtab))
+ {
+ emit shiftCtrlTabPressed();
+ return;
+ }
+
+ QWebView::keyPressEvent(event);
+}
diff --git a/src/webview.h b/src/webview.h
new file mode 100644
index 00000000..11f04571
--- /dev/null
+++ b/src/webview.h
@@ -0,0 +1,155 @@
+/* ============================================================
+*
+* This file is a part of the rekonq project
+*
+* Copyright (C) 2007-2008 Trolltech ASA. All rights reserved
+* Copyright (C) 2008 Benjamin C. Meyer <ben@meyerhome.net>
+* Copyright (C) 2008-2009 by Andrea Diamantini <adjam7 at gmail dot com>
+* Copyright (C) 2009 by Paweł Prażak <pawelprazak at gmail dot com>
+*
+*
+* This program is free software; you can redistribute it
+* and/or modify it under the terms of the GNU General
+* Public License as published by the Free Software Foundation;
+* either version 2, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+* GNU General Public License for more details.
+*
+* ============================================================ */
+
+
+#ifndef WEBVIEW_H
+#define WEBVIEW_H
+
+// KDE Includes
+#include <KUrl>
+
+// Qt Includes
+#include <QWebPage>
+
+// Forward Declarations
+class MainWindow;
+class Application;
+
+class KActionCollection;
+
+class QWebFrame;
+class QAuthenticator;
+class QMouseEvent;
+class QNetworkProxy;
+class QNetworkReply;
+class QSslError;
+
+
+class WebPage : public QWebPage
+{
+ Q_OBJECT
+
+signals:
+ void loadingUrl(const QUrl &url); // WARNING has to be QUrl!!
+
+public:
+ WebPage(QObject *parent = 0);
+ ~WebPage();
+
+protected:
+ bool acceptNavigationRequest(QWebFrame *frame,
+ const QNetworkRequest &request,
+ NavigationType type);
+
+ QWebPage *createWindow(QWebPage::WebWindowType type);
+ QObject *createPlugin(const QString &classId,
+ const QUrl &url,
+ const QStringList &paramNames,
+ const QStringList &paramValues);
+
+private slots:
+ void handleUnsupportedContent(QNetworkReply *reply);
+
+private:
+ friend class WebView;
+
+ // set the webview mousepressedevent
+ Qt::KeyboardModifiers m_keyboardModifiers;
+ Qt::MouseButtons m_pressedButtons;
+ bool m_openInNewTab;
+ KUrl m_loadingUrl;
+};
+
+
+// ----------------------------------------------------------------------------------------------------
+
+// Qt Includes
+#include <QWebView>
+
+
+class WebView : public QWebView
+{
+ Q_OBJECT
+
+public:
+ WebView(QWidget *parent = 0);
+
+ KActionCollection* webActions();
+
+ // inline
+ WebPage *webPage() const
+ {
+ return m_page;
+ }
+ KUrl url() const
+ {
+ return KUrl(QWebView::url());
+ }
+ QString lastStatusBarText() const
+ {
+ return m_statusBarText;
+ }
+ int progress() const
+ {
+ return m_progress;
+ }
+
+signals:
+ // switching tabs
+ void ctrlTabPressed();
+ void shiftCtrlTabPressed();
+
+protected:
+ void mousePressEvent(QMouseEvent *event);
+ void mouseReleaseEvent(QMouseEvent *event);
+ void contextMenuEvent(QContextMenuEvent *event);
+ void wheelEvent(QWheelEvent *event);
+
+ /**
+ * Filters (SHIFT + ) CTRL + TAB events and emit (shift)ctrlTabPressed()
+ * to make switch tab
+ */
+ void keyPressEvent(QKeyEvent *event);
+
+private slots:
+ void setProgress(int progress)
+ {
+ m_progress = progress;
+ }
+ void loadFinished();
+ void setStatusBarText(const QString &string)
+ {
+ m_statusBarText = string;
+ }
+ void downloadRequested(const QNetworkRequest &request);
+ void openLinkInNewTab();
+
+private:
+ static KActionCollection* s_webActionCollection;
+
+ WebPage *m_page;
+
+ int m_progress;
+ QString m_statusBarText;
+};
+
+#endif