diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..d38c149 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +*.swp +*~ diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..9cecc1d --- /dev/null +++ b/LICENSE @@ -0,0 +1,674 @@ + GNU GENERAL PUBLIC LICENSE + Version 3, 29 June 2007 + + Copyright (C) 2007 Free Software Foundation, Inc. + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The GNU General Public License is a free, copyleft license for +software and other kinds of works. + + The licenses for most software and other practical works are designed +to take away your freedom to share and change the works. By contrast, +the GNU General Public License is intended to guarantee your freedom to +share and change all versions of a program--to make sure it remains free +software for all its users. We, the Free Software Foundation, use the +GNU General Public License for most of our software; it applies also to +any other work released this way by its authors. You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +them if you wish), that you receive source code or can get it if you +want it, that you can change the software or use pieces of it in new +free programs, and that you know you can do these things. + + To protect your rights, we need to prevent others from denying you +these rights or asking you to surrender the rights. Therefore, you have +certain responsibilities if you distribute copies of the software, or if +you modify it: responsibilities to respect the freedom of others. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must pass on to the recipients the same +freedoms that you received. You must make sure that they, too, receive +or can get the source code. And you must show them these terms so they +know their rights. + + Developers that use the GNU GPL protect your rights with two steps: +(1) assert copyright on the software, and (2) offer you this License +giving you legal permission to copy, distribute and/or modify it. + + For the developers' and authors' protection, the GPL clearly explains +that there is no warranty for this free software. For both users' and +authors' sake, the GPL requires that modified versions be marked as +changed, so that their problems will not be attributed erroneously to +authors of previous versions. + + Some devices are designed to deny users access to install or run +modified versions of the software inside them, although the manufacturer +can do so. This is fundamentally incompatible with the aim of +protecting users' freedom to change the software. The systematic +pattern of such abuse occurs in the area of products for individuals to +use, which is precisely where it is most unacceptable. Therefore, we +have designed this version of the GPL to prohibit the practice for those +products. If such problems arise substantially in other domains, we +stand ready to extend this provision to those domains in future versions +of the GPL, as needed to protect the freedom of users. + + Finally, every program is threatened constantly by software patents. +States should not allow patents to restrict development and use of +software on general-purpose computers, but in those that do, we wish to +avoid the special danger that patents applied to a free program could +make it effectively proprietary. To prevent this, the GPL assures that +patents cannot be used to render the program non-free. + + The precise terms and conditions for copying, distribution and +modification follow. + + TERMS AND CONDITIONS + + 0. Definitions. + + "This License" refers to version 3 of the GNU General Public License. + + "Copyright" also means copyright-like laws that apply to other kinds of +works, such as semiconductor masks. + + "The Program" refers to any copyrightable work licensed under this +License. Each licensee is addressed as "you". "Licensees" and +"recipients" may be individuals or organizations. + + To "modify" a work means to copy from or adapt all or part of the work +in a fashion requiring copyright permission, other than the making of an +exact copy. The resulting work is called a "modified version" of the +earlier work or a work "based on" the earlier work. + + A "covered work" means either the unmodified Program or a work based +on the Program. + + To "propagate" a work means to do anything with it that, without +permission, would make you directly or secondarily liable for +infringement under applicable copyright law, except executing it on a +computer or modifying a private copy. Propagation includes copying, +distribution (with or without modification), making available to the +public, and in some countries other activities as well. + + To "convey" a work means any kind of propagation that enables other +parties to make or receive copies. Mere interaction with a user through +a computer network, with no transfer of a copy, is not conveying. + + An interactive user interface displays "Appropriate Legal Notices" +to the extent that it includes a convenient and prominently visible +feature that (1) displays an appropriate copyright notice, and (2) +tells the user that there is no warranty for the work (except to the +extent that warranties are provided), that licensees may convey the +work under this License, and how to view a copy of this License. If +the interface presents a list of user commands or options, such as a +menu, a prominent item in the list meets this criterion. + + 1. Source Code. + + The "source code" for a work means the preferred form of the work +for making modifications to it. "Object code" means any non-source +form of a work. + + A "Standard Interface" means an interface that either is an official +standard defined by a recognized standards body, or, in the case of +interfaces specified for a particular programming language, one that +is widely used among developers working in that language. + + The "System Libraries" of an executable work include anything, other +than the work as a whole, that (a) is included in the normal form of +packaging a Major Component, but which is not part of that Major +Component, and (b) serves only to enable use of the work with that +Major Component, or to implement a Standard Interface for which an +implementation is available to the public in source code form. A +"Major Component", in this context, means a major essential component +(kernel, window system, and so on) of the specific operating system +(if any) on which the executable work runs, or a compiler used to +produce the work, or an object code interpreter used to run it. + + The "Corresponding Source" for a work in object code form means all +the source code needed to generate, install, and (for an executable +work) run the object code and to modify the work, including scripts to +control those activities. However, it does not include the work's +System Libraries, or general-purpose tools or generally available free +programs which are used unmodified in performing those activities but +which are not part of the work. For example, Corresponding Source +includes interface definition files associated with source files for +the work, and the source code for shared libraries and dynamically +linked subprograms that the work is specifically designed to require, +such as by intimate data communication or control flow between those +subprograms and other parts of the work. + + The Corresponding Source need not include anything that users +can regenerate automatically from other parts of the Corresponding +Source. + + The Corresponding Source for a work in source code form is that +same work. + + 2. Basic Permissions. + + All rights granted under this License are granted for the term of +copyright on the Program, and are irrevocable provided the stated +conditions are met. This License explicitly affirms your unlimited +permission to run the unmodified Program. The output from running a +covered work is covered by this License only if the output, given its +content, constitutes a covered work. This License acknowledges your +rights of fair use or other equivalent, as provided by copyright law. + + You may make, run and propagate covered works that you do not +convey, without conditions so long as your license otherwise remains +in force. You may convey covered works to others for the sole purpose +of having them make modifications exclusively for you, or provide you +with facilities for running those works, provided that you comply with +the terms of this License in conveying all material for which you do +not control copyright. Those thus making or running the covered works +for you must do so exclusively on your behalf, under your direction +and control, on terms that prohibit them from making any copies of +your copyrighted material outside their relationship with you. + + Conveying under any other circumstances is permitted solely under +the conditions stated below. Sublicensing is not allowed; section 10 +makes it unnecessary. + + 3. Protecting Users' Legal Rights From Anti-Circumvention Law. + + No covered work shall be deemed part of an effective technological +measure under any applicable law fulfilling obligations under article +11 of the WIPO copyright treaty adopted on 20 December 1996, or +similar laws prohibiting or restricting circumvention of such +measures. + + When you convey a covered work, you waive any legal power to forbid +circumvention of technological measures to the extent such circumvention +is effected by exercising rights under this License with respect to +the covered work, and you disclaim any intention to limit operation or +modification of the work as a means of enforcing, against the work's +users, your or third parties' legal rights to forbid circumvention of +technological measures. + + 4. Conveying Verbatim Copies. + + You may convey verbatim copies of the Program's source code as you +receive it, in any medium, provided that you conspicuously and +appropriately publish on each copy an appropriate copyright notice; +keep intact all notices stating that this License and any +non-permissive terms added in accord with section 7 apply to the code; +keep intact all notices of the absence of any warranty; and give all +recipients a copy of this License along with the Program. + + You may charge any price or no price for each copy that you convey, +and you may offer support or warranty protection for a fee. + + 5. Conveying Modified Source Versions. + + You may convey a work based on the Program, or the modifications to +produce it from the Program, in the form of source code under the +terms of section 4, provided that you also meet all of these conditions: + + a) The work must carry prominent notices stating that you modified + it, and giving a relevant date. + + b) The work must carry prominent notices stating that it is + released under this License and any conditions added under section + 7. This requirement modifies the requirement in section 4 to + "keep intact all notices". + + c) You must license the entire work, as a whole, under this + License to anyone who comes into possession of a copy. This + License will therefore apply, along with any applicable section 7 + additional terms, to the whole of the work, and all its parts, + regardless of how they are packaged. This License gives no + permission to license the work in any other way, but it does not + invalidate such permission if you have separately received it. + + d) If the work has interactive user interfaces, each must display + Appropriate Legal Notices; however, if the Program has interactive + interfaces that do not display Appropriate Legal Notices, your + work need not make them do so. + + A compilation of a covered work with other separate and independent +works, which are not by their nature extensions of the covered work, +and which are not combined with it such as to form a larger program, +in or on a volume of a storage or distribution medium, is called an +"aggregate" if the compilation and its resulting copyright are not +used to limit the access or legal rights of the compilation's users +beyond what the individual works permit. Inclusion of a covered work +in an aggregate does not cause this License to apply to the other +parts of the aggregate. + + 6. Conveying Non-Source Forms. + + You may convey a covered work in object code form under the terms +of sections 4 and 5, provided that you also convey the +machine-readable Corresponding Source under the terms of this License, +in one of these ways: + + a) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by the + Corresponding Source fixed on a durable physical medium + customarily used for software interchange. + + b) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by a + written offer, valid for at least three years and valid for as + long as you offer spare parts or customer support for that product + model, to give anyone who possesses the object code either (1) a + copy of the Corresponding Source for all the software in the + product that is covered by this License, on a durable physical + medium customarily used for software interchange, for a price no + more than your reasonable cost of physically performing this + conveying of source, or (2) access to copy the + Corresponding Source from a network server at no charge. + + c) Convey individual copies of the object code with a copy of the + written offer to provide the Corresponding Source. This + alternative is allowed only occasionally and noncommercially, and + only if you received the object code with such an offer, in accord + with subsection 6b. + + d) Convey the object code by offering access from a designated + place (gratis or for a charge), and offer equivalent access to the + Corresponding Source in the same way through the same place at no + further charge. You need not require recipients to copy the + Corresponding Source along with the object code. If the place to + copy the object code is a network server, the Corresponding Source + may be on a different server (operated by you or a third party) + that supports equivalent copying facilities, provided you maintain + clear directions next to the object code saying where to find the + Corresponding Source. Regardless of what server hosts the + Corresponding Source, you remain obligated to ensure that it is + available for as long as needed to satisfy these requirements. + + e) Convey the object code using peer-to-peer transmission, provided + you inform other peers where the object code and Corresponding + Source of the work are being offered to the general public at no + charge under subsection 6d. + + A separable portion of the object code, whose source code is excluded +from the Corresponding Source as a System Library, need not be +included in conveying the object code work. + + A "User Product" is either (1) a "consumer product", which means any +tangible personal property which is normally used for personal, family, +or household purposes, or (2) anything designed or sold for incorporation +into a dwelling. In determining whether a product is a consumer product, +doubtful cases shall be resolved in favor of coverage. For a particular +product received by a particular user, "normally used" refers to a +typical or common use of that class of product, regardless of the status +of the particular user or of the way in which the particular user +actually uses, or expects or is expected to use, the product. A product +is a consumer product regardless of whether the product has substantial +commercial, industrial or non-consumer uses, unless such uses represent +the only significant mode of use of the product. + + "Installation Information" for a User Product means any methods, +procedures, authorization keys, or other information required to install +and execute modified versions of a covered work in that User Product from +a modified version of its Corresponding Source. The information must +suffice to ensure that the continued functioning of the modified object +code is in no case prevented or interfered with solely because +modification has been made. + + If you convey an object code work under this section in, or with, or +specifically for use in, a User Product, and the conveying occurs as +part of a transaction in which the right of possession and use of the +User Product is transferred to the recipient in perpetuity or for a +fixed term (regardless of how the transaction is characterized), the +Corresponding Source conveyed under this section must be accompanied +by the Installation Information. But this requirement does not apply +if neither you nor any third party retains the ability to install +modified object code on the User Product (for example, the work has +been installed in ROM). + + The requirement to provide Installation Information does not include a +requirement to continue to provide support service, warranty, or updates +for a work that has been modified or installed by the recipient, or for +the User Product in which it has been modified or installed. Access to a +network may be denied when the modification itself materially and +adversely affects the operation of the network or violates the rules and +protocols for communication across the network. + + Corresponding Source conveyed, and Installation Information provided, +in accord with this section must be in a format that is publicly +documented (and with an implementation available to the public in +source code form), and must require no special password or key for +unpacking, reading or copying. + + 7. Additional Terms. + + "Additional permissions" are terms that supplement the terms of this +License by making exceptions from one or more of its conditions. +Additional permissions that are applicable to the entire Program shall +be treated as though they were included in this License, to the extent +that they are valid under applicable law. If additional permissions +apply only to part of the Program, that part may be used separately +under those permissions, but the entire Program remains governed by +this License without regard to the additional permissions. + + When you convey a copy of a covered work, you may at your option +remove any additional permissions from that copy, or from any part of +it. (Additional permissions may be written to require their own +removal in certain cases when you modify the work.) You may place +additional permissions on material, added by you to a covered work, +for which you have or can give appropriate copyright permission. + + Notwithstanding any other provision of this License, for material you +add to a covered work, you may (if authorized by the copyright holders of +that material) supplement the terms of this License with terms: + + a) Disclaiming warranty or limiting liability differently from the + terms of sections 15 and 16 of this License; or + + b) Requiring preservation of specified reasonable legal notices or + author attributions in that material or in the Appropriate Legal + Notices displayed by works containing it; or + + c) Prohibiting misrepresentation of the origin of that material, or + requiring that modified versions of such material be marked in + reasonable ways as different from the original version; or + + d) Limiting the use for publicity purposes of names of licensors or + authors of the material; or + + e) Declining to grant rights under trademark law for use of some + trade names, trademarks, or service marks; or + + f) Requiring indemnification of licensors and authors of that + material by anyone who conveys the material (or modified versions of + it) with contractual assumptions of liability to the recipient, for + any liability that these contractual assumptions directly impose on + those licensors and authors. + + All other non-permissive additional terms are considered "further +restrictions" within the meaning of section 10. If the Program as you +received it, or any part of it, contains a notice stating that it is +governed by this License along with a term that is a further +restriction, you may remove that term. If a license document contains +a further restriction but permits relicensing or conveying under this +License, you may add to a covered work material governed by the terms +of that license document, provided that the further restriction does +not survive such relicensing or conveying. + + If you add terms to a covered work in accord with this section, you +must place, in the relevant source files, a statement of the +additional terms that apply to those files, or a notice indicating +where to find the applicable terms. + + Additional terms, permissive or non-permissive, may be stated in the +form of a separately written license, or stated as exceptions; +the above requirements apply either way. + + 8. Termination. + + You may not propagate or modify a covered work except as expressly +provided under this License. Any attempt otherwise to propagate or +modify it is void, and will automatically terminate your rights under +this License (including any patent licenses granted under the third +paragraph of section 11). + + However, if you cease all violation of this License, then your +license from a particular copyright holder is reinstated (a) +provisionally, unless and until the copyright holder explicitly and +finally terminates your license, and (b) permanently, if the copyright +holder fails to notify you of the violation by some reasonable means +prior to 60 days after the cessation. + + Moreover, your license from a particular copyright holder is +reinstated permanently if the copyright holder notifies you of the +violation by some reasonable means, this is the first time you have +received notice of violation of this License (for any work) from that +copyright holder, and you cure the violation prior to 30 days after +your receipt of the notice. + + Termination of your rights under this section does not terminate the +licenses of parties who have received copies or rights from you under +this License. If your rights have been terminated and not permanently +reinstated, you do not qualify to receive new licenses for the same +material under section 10. + + 9. Acceptance Not Required for Having Copies. + + You are not required to accept this License in order to receive or +run a copy of the Program. Ancillary propagation of a covered work +occurring solely as a consequence of using peer-to-peer transmission +to receive a copy likewise does not require acceptance. However, +nothing other than this License grants you permission to propagate or +modify any covered work. These actions infringe copyright if you do +not accept this License. Therefore, by modifying or propagating a +covered work, you indicate your acceptance of this License to do so. + + 10. Automatic Licensing of Downstream Recipients. + + Each time you convey a covered work, the recipient automatically +receives a license from the original licensors, to run, modify and +propagate that work, subject to this License. You are not responsible +for enforcing compliance by third parties with this License. + + An "entity transaction" is a transaction transferring control of an +organization, or substantially all assets of one, or subdividing an +organization, or merging organizations. If propagation of a covered +work results from an entity transaction, each party to that +transaction who receives a copy of the work also receives whatever +licenses to the work the party's predecessor in interest had or could +give under the previous paragraph, plus a right to possession of the +Corresponding Source of the work from the predecessor in interest, if +the predecessor has it or can get it with reasonable efforts. + + You may not impose any further restrictions on the exercise of the +rights granted or affirmed under this License. For example, you may +not impose a license fee, royalty, or other charge for exercise of +rights granted under this License, and you may not initiate litigation +(including a cross-claim or counterclaim in a lawsuit) alleging that +any patent claim is infringed by making, using, selling, offering for +sale, or importing the Program or any portion of it. + + 11. Patents. + + A "contributor" is a copyright holder who authorizes use under this +License of the Program or a work on which the Program is based. The +work thus licensed is called the contributor's "contributor version". + + A contributor's "essential patent claims" are all patent claims +owned or controlled by the contributor, whether already acquired or +hereafter acquired, that would be infringed by some manner, permitted +by this License, of making, using, or selling its contributor version, +but do not include claims that would be infringed only as a +consequence of further modification of the contributor version. For +purposes of this definition, "control" includes the right to grant +patent sublicenses in a manner consistent with the requirements of +this License. + + Each contributor grants you a non-exclusive, worldwide, royalty-free +patent license under the contributor's essential patent claims, to +make, use, sell, offer for sale, import and otherwise run, modify and +propagate the contents of its contributor version. + + In the following three paragraphs, a "patent license" is any express +agreement or commitment, however denominated, not to enforce a patent +(such as an express permission to practice a patent or covenant not to +sue for patent infringement). To "grant" such a patent license to a +party means to make such an agreement or commitment not to enforce a +patent against the party. + + If you convey a covered work, knowingly relying on a patent license, +and the Corresponding Source of the work is not available for anyone +to copy, free of charge and under the terms of this License, through a +publicly available network server or other readily accessible means, +then you must either (1) cause the Corresponding Source to be so +available, or (2) arrange to deprive yourself of the benefit of the +patent license for this particular work, or (3) arrange, in a manner +consistent with the requirements of this License, to extend the patent +license to downstream recipients. "Knowingly relying" means you have +actual knowledge that, but for the patent license, your conveying the +covered work in a country, or your recipient's use of the covered work +in a country, would infringe one or more identifiable patents in that +country that you have reason to believe are valid. + + If, pursuant to or in connection with a single transaction or +arrangement, you convey, or propagate by procuring conveyance of, a +covered work, and grant a patent license to some of the parties +receiving the covered work authorizing them to use, propagate, modify +or convey a specific copy of the covered work, then the patent license +you grant is automatically extended to all recipients of the covered +work and works based on it. + + A patent license is "discriminatory" if it does not include within +the scope of its coverage, prohibits the exercise of, or is +conditioned on the non-exercise of one or more of the rights that are +specifically granted under this License. You may not convey a covered +work if you are a party to an arrangement with a third party that is +in the business of distributing software, under which you make payment +to the third party based on the extent of your activity of conveying +the work, and under which the third party grants, to any of the +parties who would receive the covered work from you, a discriminatory +patent license (a) in connection with copies of the covered work +conveyed by you (or copies made from those copies), or (b) primarily +for and in connection with specific products or compilations that +contain the covered work, unless you entered into that arrangement, +or that patent license was granted, prior to 28 March 2007. + + Nothing in this License shall be construed as excluding or limiting +any implied license or other defenses to infringement that may +otherwise be available to you under applicable patent law. + + 12. No Surrender of Others' Freedom. + + If conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot convey a +covered work so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you may +not convey it at all. For example, if you agree to terms that obligate you +to collect a royalty for further conveying from those to whom you convey +the Program, the only way you could satisfy both those terms and this +License would be to refrain entirely from conveying the Program. + + 13. Use with the GNU Affero General Public License. + + Notwithstanding any other provision of this License, you have +permission to link or combine any covered work with a work licensed +under version 3 of the GNU Affero General Public License into a single +combined work, and to convey the resulting work. The terms of this +License will continue to apply to the part which is the covered work, +but the special requirements of the GNU Affero General Public License, +section 13, concerning interaction through a network will apply to the +combination as such. + + 14. Revised Versions of this License. + + The Free Software Foundation may publish revised and/or new versions of +the GNU General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + + Each version is given a distinguishing version number. If the +Program specifies that a certain numbered version of the GNU General +Public License "or any later version" applies to it, you have the +option of following the terms and conditions either of that numbered +version or of any later version published by the Free Software +Foundation. If the Program does not specify a version number of the +GNU General Public License, you may choose any version ever published +by the Free Software Foundation. + + If the Program specifies that a proxy can decide which future +versions of the GNU General Public License can be used, that proxy's +public statement of acceptance of a version permanently authorizes you +to choose that version for the Program. + + Later license versions may give you additional or different +permissions. However, no additional obligations are imposed on any +author or copyright holder as a result of your choosing to follow a +later version. + + 15. Disclaimer of Warranty. + + THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY +APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT +HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY +OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, +THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM +IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF +ALL NECESSARY SERVICING, REPAIR OR CORRECTION. + + 16. Limitation of Liability. + + IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS +THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY +GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE +USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF +DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD +PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), +EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF +SUCH DAMAGES. + + 17. Interpretation of Sections 15 and 16. + + If the disclaimer of warranty and limitation of liability provided +above cannot be given local legal effect according to their terms, +reviewing courts shall apply local law that most closely approximates +an absolute waiver of all civil liability in connection with the +Program, unless a warranty or assumption of liability accompanies a +copy of the Program in return for a fee. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +state the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + {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 . + +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: + + {project} Copyright (C) {year} {fullname} + This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, your program's commands +might be different; for a GUI interface, you would use an "about box". + + You should also get your employer (if you work as a programmer) or school, +if any, to sign a "copyright disclaimer" for the program, if necessary. +For more information on this, and how to apply and follow the GNU GPL, see +. + + The GNU General Public License does not permit incorporating your program +into proprietary programs. If your program is a subroutine library, you +may consider it more useful to permit linking proprietary applications with +the library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. But first, please read +. diff --git a/README.md b/README.md index acb8055..daed933 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,32 @@ -# mytinytodo_ynh -myTinyTodo for YunoHost / LabriqueInternet +# MyTinyTodo for Yunohost + + * en : A **simple** way to manage your todo list. + * fr : Un simple, mais **efficace** script de gestion de todo list (*GTD*). + * [Original Site](http://www.mytinytodo.net/) + * [Demo](http://www.mytinytodo.net/) + * [Demo for mobile](http://www.mytinytodo.net/) + +## En image : + +![capture mytinytodo](https://framapic.org/kHD4bcOGCnam/p7uc1rDT1B9j.png) + +## Francais : + +Pour le moment, je pars sur une installation simple. + + * pas de multi-instance, + * mysql/mariadb uniquement (pas de sqlite), + * gestion des langues (fr, en, de, ru). + +## Anglais : + + * à faire. + +## Astuces : + + * Pour saisir rapidement une tâche, avec une priorité et des mots clefs + +```python +/+2/ Faire la traduction en anglais du README.md /#yunohost, mytinytodo/ +``` + diff --git a/conf/config.php b/conf/config.php new file mode 100755 index 0000000..672a4c1 --- /dev/null +++ b/conf/config.php @@ -0,0 +1,26 @@ + diff --git a/conf/nginx.conf b/conf/nginx.conf new file mode 100644 index 0000000..91394b5 --- /dev/null +++ b/conf/nginx.conf @@ -0,0 +1,34 @@ +#--MULTISITE--if (!-e $request_filename) { + #--MULTISITE--rewrite /wp-admin$ $scheme://$host$uri/ permanent; + #--MULTISITE--rewrite ^__PATHTOCHANGE__(/[^/]+)?(/wp-.*) __PATHTOCHANGE__$2 last; + #--MULTISITE--rewrite ^__PATHTOCHANGE__(/[^/]+)?(/.*\.php)$ __PATHTOCHANGE__$2 last; +#--MULTISITE--} + +location __PATHTOCHANGE__ { + alias __FINALPATH__/; + index index.php; + #if (!-e $request_filename) + #{ + # rewrite ^(.+)$ __PATHTOCHANGE__/index.php?q=$1 last; + #} + #if ($scheme = http) { + # rewrite ^ https://$server_name$request_uri? permanent; + #} + #client_max_body_size 30m; + + try_files $uri $uri/ __PATHTOCHANGE__/index.php?$args; + + location ~ [^/]\.php(/|$) { + fastcgi_split_path_info ^(.+?\.php)(/.*)$; + #fastcgi_pass unix:/var/run/php5-fpm-__NAMETOCHANGE__.sock; + fastcgi_pass unix:/var/run/php5-fpm.sock; + fastcgi_index index.php; + include fastcgi_params; + fastcgi_param REMOTE_USER $remote_user; + fastcgi_param PATH_INFO $fastcgi_path_info; + fastcgi_param SCRIPT_FILENAME $request_filename; + } + + #--PRIVATE--# Include SSOWAT user panel. + #--PRIVATE--include conf.d/yunohost_panel.conf.inc; +} diff --git a/conf/sql/mytinytodo.sql b/conf/sql/mytinytodo.sql new file mode 100644 index 0000000..a13fc37 --- /dev/null +++ b/conf/sql/mytinytodo.sql @@ -0,0 +1,149 @@ +-- phpMyAdmin SQL Dump +-- version 4.6.6 +-- https://www.phpmyadmin.net/ +-- +-- Client : localhost +-- Généré le : Mar 21 Mars 2017 à 06:57 +-- Version du serveur : 10.0.30-MariaDB-0+deb8u1 +-- Version de PHP : 5.6.30-0+deb8u1 + +SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO"; +SET time_zone = "+00:00"; + + +/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */; +/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */; +/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */; +/*!40101 SET NAMES utf8mb4 */; + +-- +-- Base de données : `mytinytodo` +-- + +-- -------------------------------------------------------- + +-- +-- Structure de la table `mtt_lists` +-- + +CREATE TABLE `mtt_lists` ( + `id` int(10) UNSIGNED NOT NULL, + `uuid` char(36) NOT NULL DEFAULT '', + `ow` int(11) NOT NULL DEFAULT '0', + `name` varchar(50) NOT NULL DEFAULT '', + `d_created` int(10) UNSIGNED NOT NULL DEFAULT '0', + `d_edited` int(10) UNSIGNED NOT NULL DEFAULT '0', + `sorting` tinyint(3) UNSIGNED NOT NULL DEFAULT '0', + `published` tinyint(3) UNSIGNED NOT NULL DEFAULT '0', + `taskview` int(10) UNSIGNED NOT NULL DEFAULT '0' +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + +-- +-- Contenu de la table `mtt_lists` +-- + +INSERT INTO `mtt_lists` (`id`, `uuid`, `ow`, `name`, `d_created`, `d_edited`, `sorting`, `published`, `taskview`) VALUES +(1, 'ad9ad4a6-032a-4e44-979f-b7feebc73c1a', 0, 'Todo', 1490075778, 0, 0, 0, 0); + +-- -------------------------------------------------------- + +-- +-- Structure de la table `mtt_tag2task` +-- + +CREATE TABLE `mtt_tag2task` ( + `tag_id` int(10) UNSIGNED NOT NULL, + `task_id` int(10) UNSIGNED NOT NULL, + `list_id` int(10) UNSIGNED NOT NULL +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + +-- -------------------------------------------------------- + +-- +-- Structure de la table `mtt_tags` +-- + +CREATE TABLE `mtt_tags` ( + `id` int(10) UNSIGNED NOT NULL, + `name` varchar(50) NOT NULL +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + +-- -------------------------------------------------------- + +-- +-- Structure de la table `mtt_todolist` +-- + +CREATE TABLE `mtt_todolist` ( + `id` int(10) UNSIGNED NOT NULL, + `uuid` char(36) NOT NULL DEFAULT '', + `list_id` int(10) UNSIGNED NOT NULL DEFAULT '0', + `d_created` int(10) UNSIGNED NOT NULL DEFAULT '0', + `d_completed` int(10) UNSIGNED NOT NULL DEFAULT '0', + `d_edited` int(10) UNSIGNED NOT NULL DEFAULT '0', + `compl` tinyint(3) UNSIGNED NOT NULL DEFAULT '0', + `title` varchar(250) NOT NULL, + `note` text, + `prio` tinyint(4) NOT NULL DEFAULT '0', + `ow` int(11) NOT NULL DEFAULT '0', + `tags` varchar(600) NOT NULL DEFAULT '', + `tags_ids` varchar(250) NOT NULL DEFAULT '', + `duedate` date DEFAULT NULL +) ENGINE=InnoDB DEFAULT CHARSET=utf8; + +-- +-- Index pour les tables exportées +-- + +-- +-- Index pour la table `mtt_lists` +-- +ALTER TABLE `mtt_lists` + ADD PRIMARY KEY (`id`), + ADD UNIQUE KEY `uuid` (`uuid`); + +-- +-- Index pour la table `mtt_tag2task` +-- +ALTER TABLE `mtt_tag2task` + ADD KEY `tag_id` (`tag_id`), + ADD KEY `task_id` (`task_id`), + ADD KEY `list_id` (`list_id`); + +-- +-- Index pour la table `mtt_tags` +-- +ALTER TABLE `mtt_tags` + ADD PRIMARY KEY (`id`), + ADD UNIQUE KEY `name` (`name`); + +-- +-- Index pour la table `mtt_todolist` +-- +ALTER TABLE `mtt_todolist` + ADD PRIMARY KEY (`id`), + ADD UNIQUE KEY `uuid` (`uuid`), + ADD KEY `list_id` (`list_id`); + +-- +-- AUTO_INCREMENT pour les tables exportées +-- + +-- +-- AUTO_INCREMENT pour la table `mtt_lists` +-- +ALTER TABLE `mtt_lists` + MODIFY `id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=2; +-- +-- AUTO_INCREMENT pour la table `mtt_tags` +-- +ALTER TABLE `mtt_tags` + MODIFY `id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT; +-- +-- AUTO_INCREMENT pour la table `mtt_todolist` +-- +ALTER TABLE `mtt_todolist` + MODIFY `id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT; +/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */; +/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */; +/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; diff --git a/manifest.json b/manifest.json new file mode 100644 index 0000000..8cbaaa0 --- /dev/null +++ b/manifest.json @@ -0,0 +1,67 @@ +{ + "name": "myTinyTodo", + "id": "mytinytodo", + "packaging_format": 1, + "description": { + "en": "Simple open source to-do list script.", + "fr": "Un simple mais efficace script de gestion de todo list (gtd)." + }, + "url": "http://www.mytinytodo.net/", + "license": "free", + "maintainer": { + "name": "plabuse", + "email": "plabuse@opmbx.org" + }, + "requirements": { + "yunohost": ">= 2.5.6" + }, + "multi_instance": false, + "services": [ + "nginx", + "php5-fpm", + "mysql" + ], + "arguments": { + "install" : [ + { + "name": "domain", + "type": "domain", + "ask": { + "en": "Choose a domain name for mytinytodo", + "fr": "Choisissez un nom de domaine pour mytinytodo" + }, + "example": "domaine.org" + }, + { + "name": "path", + "type": "path", + "ask": { + "en": "Choose a path for mytinytodo", + "fr": "Choisissez un chemin pour mytinytodo" + }, + "example": "/mytinytodo", + "default": "/mytinytodo" + }, + { + "name": "is_public", + "type": "boolean", + "ask": { + "en": "Is it a public application?", + "fr": "Est-ce une application publique ?" + }, + "default": true + }, + { + "name": "language", + "ask": { + "en": "Choose the application language", + "ru": "Выберите язык приложения", + "de": "Wählen Sie die Sprache der Anwendung", + "fr": "Choisissez la langue de l'application" + }, + "choices": ["fr", "en", "de", "ru"], + "default": "fr" + } + ] + } +} diff --git a/scripts/_common.sh b/scripts/_common.sh new file mode 100644 index 0000000..20e53fb --- /dev/null +++ b/scripts/_common.sh @@ -0,0 +1,508 @@ +#!/bin/bash + +#================================================= +# CHECKING +#================================================= + +CHECK_USER () { # Vérifie la validité de l'user admin +# $1 = Variable de l'user admin. + ynh_user_exists "$1" || ynh_die "Wrong user" +} + +CHECK_DOMAINPATH () { # Vérifie la disponibilité du path et du domaine. + sudo yunohost app checkurl $domain$path_url -a $app +} + +CHECK_FINALPATH () { # Vérifie que le dossier de destination n'est pas déjà utilisé. + final_path=/var/www/$app + test ! -e "$final_path" || ynh_die "This path already contains a folder" +} + +#================================================= +# DISPLAYING +#================================================= + +NO_PRINT () { # Supprime l'affichage dans stdout pour la commande en argument. + set +x + $@ + set -x +} + +WARNING () { # Écrit sur le canal d'erreur pour passer en warning. + $@ >&2 +} + +SUPPRESS_WARNING () { # Force l'écriture sur la sortie standard + $@ 2>&1 +} + +QUIET () { # Redirige la sortie standard dans /dev/null + $@ > /dev/null +} + +ALL_QUIET () { # Redirige la sortie standard et d'erreur dans /dev/null + $@ > /dev/null 2>&1 +} + +#================================================= +# SETUP +#================================================= + +SETUP_SOURCE () { # Télécharge la source, décompresse et copie dans $final_path + src_url=$(cat ../conf/app.src | grep SOURCE_URL | cut -d'>' -f2) + src_checksum=$(cat ../conf/app.src | grep SOURCE_SUM | cut -d= -f2) + # Download sources from the upstream + wget -nv -O source.tar.gz $src_url + # Vérifie la somme de contrôle de la source téléchargée. + echo "$src_checksum source.tar.gz" | md5sum -c --status || ynh_die "Corrupt source" + # Extract source into the app dir + sudo mkdir -p $final_path + sudo tar -x -f source.tar.gz -C $final_path --strip-components 1 + # Copie les fichiers additionnels ou modifiés. + if test -e "../sources/ajouts"; then + sudo cp -a ../sources/ajouts/. "$final_path" + fi +} + +SETUP_SOURCE_ZIP () { # Télécharge la source, décompresse et copie dans $final_path + src_url=$(cat ../conf/app.src | grep SOURCE_URL | cut -d'>' -f2) + src_checksum=$(cat ../conf/app.src | grep SOURCE_SUM | cut -d= -f2) + # Download sources from the upstream + wget -nv -O source.zip $src_url + # Vérifie la somme de contrôle de la source téléchargée. + echo "$src_checksum source.zip" | md5sum -c --status || ynh_die "Corrupt source" + # Extract source into the app dir + sudo mkdir -p $final_path + temp_dir=$(mktemp -d) + unzip -quo source.zip -d $temp_dir # On passe par un dossier temporaire car unzip ne permet pas d'ignorer le dossier parent. + sudo cp -a $temp_dir/*/. $final_path + rm -r $temp_dir + # Copie les fichiers additionnels ou modifiés. + if test -e "../sources/ajouts"; then + sudo cp -a ../sources/ajouts/. "$final_path" + fi +} + +POOL_FPM () { # Créer le fichier de configuration du pool php-fpm et le configure. + sed -i "s@__NAMETOCHANGE__@$app@g" ../conf/php-fpm.conf + sed -i "s@__FINALPATH__@$final_path@g" ../conf/php-fpm.conf + sed -i "s@__USER__@$app@g" ../conf/php-fpm.conf + finalphpconf=/etc/php5/fpm/pool.d/$app.conf + sudo cp ../conf/php-fpm.conf $finalphpconf + sudo chown root: $finalphpconf + finalphpini=/etc/php5/fpm/conf.d/20-$app.ini + sudo cp ../conf/php-fpm.ini $finalphpini + sudo chown root: $finalphpini + sudo systemctl reload php5-fpm +} + +YNH_CURL () { + data_post=$1 + url_access=$2 + sleep 1 + curl -kL -H "Host: $domain" --resolve $domain:443:127.0.0.1 --data "$data_post" "https://localhost$path_url$url_access" 2>&1 +} + +#================================================= +# REMOVE +#================================================= + +REMOVE_NGINX_CONF () { # Suppression de la configuration nginx + if [ -e "/etc/nginx/conf.d/$domain.d/$app.conf" ]; then # Delete nginx config + echo "Delete nginx config" + sudo rm "/etc/nginx/conf.d/$domain.d/$app.conf" + sudo systemctl reload nginx + fi +} + +REMOVE_FPM_CONF () { # Suppression de la configuration du pool php-fpm + if [ -e "/etc/php5/fpm/pool.d/$app.conf" ]; then # Delete fpm config + echo "Delete fpm config" + sudo rm "/etc/php5/fpm/pool.d/$app.conf" + fi + if [ -e "/etc/php5/fpm/conf.d/20-$app.ini" ]; then # Delete php config + echo "Delete php config" + sudo rm "/etc/php5/fpm/conf.d/20-$app.ini" + fi + sudo systemctl reload php5-fpm +} + +SECURE_REMOVE () { # Suppression de dossier avec vérification des variables + chaine="$1" # L'argument doit être donné entre quotes simple '', pour éviter d'interpréter les variables. + no_var=0 + while (echo "$chaine" | grep -q '\$') # Boucle tant qu'il y a des $ dans la chaine + do + no_var=1 + global_var=$(echo "$chaine" | cut -d '$' -f 2) # Isole la première variable trouvée. + only_var=\$$(expr "$global_var" : '\([A-Za-z0-9_]*\)') # Isole complètement la variable en ajoutant le $ au début et en gardant uniquement le nom de la variable. Se débarrasse surtout du / et d'un éventuel chemin derrière. + real_var=$(eval "echo ${only_var}") # `eval "echo ${var}` permet d'interpréter une variable contenue dans une variable. + if test -z "$real_var" || [ "$real_var" = "/" ]; then + WARNING echo "Variable $only_var is empty, suppression of $chaine cancelled." + return 1 + fi + chaine=$(echo "$chaine" | sed "s@$only_var@$real_var@") # remplace la variable par sa valeur dans la chaine. + done + if [ "$no_var" -eq 1 ] + then + if [ -e "$chaine" ]; then + echo "Delete directory $chaine" + sudo rm -r "$chaine" + fi + return 0 + else + WARNING echo "No detected variable." + return 1 + fi +} + +#================================================= +# BACKUP +#================================================= + +BACKUP_FAIL_UPGRADE () { + WARNING echo "Upgrade failed." + app_bck=${app//_/-} # Replace all '_' by '-' + if sudo yunohost backup list | grep -q $app_bck-pre-upgrade$backup_number; then # Vérifie l'existence de l'archive avant de supprimer l'application et de restaurer + sudo yunohost app remove $app # Supprime l'application avant de la restaurer. + sudo yunohost backup restore --ignore-hooks $app_bck-pre-upgrade$backup_number --apps $app --force # Restore the backup if upgrade failed + ynh_die "The app was restored to the way it was before the failed upgrade." + fi +} + +BACKUP_BEFORE_UPGRADE () { # Backup the current version of the app, restore it if the upgrade fails + backup_number=1 + old_backup_number=2 + app_bck=${app//_/-} # Replace all '_' by '-' + if sudo yunohost backup list | grep -q $app_bck-pre-upgrade1; then # Vérifie l'existence d'une archive déjà numéroté à 1. + backup_number=2 # Et passe le numéro de l'archive à 2 + old_backup_number=1 + fi + + sudo yunohost backup create --ignore-hooks --apps $app --name $app_bck-pre-upgrade$backup_number # Créer un backup différent de celui existant. + if [ "$?" -eq 0 ]; then # Si le backup est un succès, supprime l'archive précédente. + if sudo yunohost backup list | grep -q $app_bck-pre-upgrade$old_backup_number; then # Vérifie l'existence de l'ancienne archive avant de la supprimer, pour éviter une erreur. + QUIET sudo yunohost backup delete $app_bck-pre-upgrade$old_backup_number + fi + else # Si le backup a échoué + ynh_die "Backup failed, the upgrade process was aborted." + fi +} + +HUMAN_SIZE () { # Transforme une taille en Ko en une taille lisible pour un humain + human=$(numfmt --to=iec --from-unit=1K $1) + echo $human +} + +CHECK_SIZE () { # Vérifie avant chaque backup que l'espace est suffisant + file_to_analyse=$1 + backup_size=$(sudo du --summarize "$file_to_analyse" | cut -f1) + free_space=$(sudo df --output=avail "/home/yunohost.backup" | sed 1d) + + if [ $free_space -le $backup_size ] + then + WARNING echo "Espace insuffisant pour sauvegarder $file_to_analyse." + WARNING echo "Espace disponible: $(HUMAN_SIZE $free_space)" + ynh_die "Espace nécessaire: $(HUMAN_SIZE $backup_size)" + fi +} + +#================================================= +# CONFIGURATION +#================================================= + +STORE_MD5_CONFIG () { # Enregistre la somme de contrôle du fichier de config +# $1 = Nom du fichier de conf pour le stockage dans settings.yml +# $2 = Nom complet et chemin du fichier de conf. + ynh_app_setting_set $app $1_file_md5 $(sudo md5sum "$2" | cut -d' ' -f1) +} + +CHECK_MD5_CONFIG () { # Créé un backup du fichier de config si il a été modifié. +# $1 = Nom du fichier de conf pour le stockage dans settings.yml +# $2 = Nom complet et chemin du fichier de conf. + if [ "$(ynh_app_setting_get $app $1_file_md5)" != $(sudo md5sum "$2" | cut -d' ' -f1) ]; then + sudo cp -a "$2" "$2.backup.$(date '+%d.%m.%y_%Hh%M,%Ss')" # Si le fichier de config a été modifié, créer un backup. + fi +} + +#================================================= +# PACKAGE CHECK BYPASSING... +#================================================= + +IS_PACKAGE_CHECK () { # Détermine une exécution en conteneur (Non testé) + return uname -n | grep -c 'pchecker_lxc' +} + +#================================================= +#================================================= +# FUTUR YNH HELPERS +#================================================= +# Importer ce fichier de fonction avant celui des helpers officiel +# Ainsi, les officiels prendront le pas sur ceux-ci le cas échéant +#================================================= + +# Ignore the yunohost-cli log to prevent errors with conditionals commands +# usage: ynh_no_log COMMAND +# Simply duplicate the log, execute the yunohost command and replace the log without the result of this command +# It's a very badly hack... +ynh_no_log() { + ynh_cli_log=/var/log/yunohost/yunohost-cli.log + sudo cp -a ${ynh_cli_log} ${ynh_cli_log}-move + eval $@ + exit_code=$? + sudo mv ${ynh_cli_log}-move ${ynh_cli_log} + return $? +} + +# Normalize the url path syntax +# Handle the slash at the beginning of path and its absence at ending +# Return a normalized url path +# +# example: url_path=$(ynh_normalize_url_path $url_path) +# ynh_normalize_url_path example -> /example +# ynh_normalize_url_path /example -> /example +# ynh_normalize_url_path /example/ -> /example +# +# usage: ynh_normalize_url_path path_to_normalize +# | arg: url_path_to_normalize - URL path to normalize before using it +ynh_normalize_url_path () { + path_url=$1 + test -n "$path_url" || ynh_die "ynh_normalize_url_path expect a URL path as first argument and received nothing." + if [ "${path_url:0:1}" != "/" ]; then # If the first character is not a / + path_url="/$path_url" # Add / at begin of path variable + fi + if [ "${path_url:${#path_url}-1}" == "/" ] && [ ${#path_url} -gt 1 ]; then # If the last character is a / and that not the only character. + path_url="${path_url:0:${#path_url}-1}" # Delete the last character + fi + echo $path_url +} + +# Create a database, an user and its password. Then store the password in the app's config +# +# User of database will be store in db_user's variable. +# Name of database will be store in db_name's variable. +# And password in db_pwd's variable. +# +# usage: ynh_mysql_generate_db user name +# | arg: user - Owner of the database +# | arg: name - Name of the database +ynh_mysql_generate_db () { + db_pwd=$(ynh_string_random) # Generate a random password + ynh_mysql_create_db "$2" "$1" "$db_pwd" # Create the database + ynh_app_setting_set $app mysqlpwd $db_pwd # Store the password in the app's config +} + +# Remove a database if it exist and the associated user +# +# usage: ynh_mysql_remove_db user name +# | arg: user - Proprietary of the database +# | arg: name - Name of the database +ynh_mysql_remove_db () { + if mysqlshow -u root -p$(sudo cat $MYSQL_ROOT_PWD_FILE) | grep -q "^| $2"; then # Check if the database exist + echo "Remove database $2" >&2 + ynh_mysql_drop_db $2 # Remove the database + ynh_mysql_drop_user $1 # Remove the associated user to database + else + echo "Database $2 not found" >&2 + fi +} + +# Correct the name given in argument for mariadb +# +# Avoid invalid name for your database +# +# Exemple: dbname=$(ynh_make_valid_dbid $app) +# +# usage: ynh_make_valid_dbid name +# | arg: name - name to correct +# | ret: the corrected name +ynh_make_valid_dbid () { + dbid=${1//[-.]/_} # Mariadb doesn't support - and . in the name of databases. It will be replace by _ + echo $dbid +} + +# Manage a fail of the script +# +# Print a warning to inform that the script was failed +# Execute the ynh_clean_setup function if used in the app script +# +# usage of ynh_clean_setup function +# This function provide a way to clean some residual of installation that not managed by remove script. +# To use it, simply add in your script: +# ynh_clean_setup () { +# instructions... +# } +# This function is optionnal. +# +# Usage: ynh_exit_properly is used only by the helper ynh_check_error. +# You must not use it directly. +ynh_exit_properly () { + exit_code=$? + if [ "$exit_code" -eq 0 ]; then + exit 0 # Exit without error if the script ended correctly + fi + + trap '' EXIT # Ignore new exit signals + set +eu # Do not exit anymore if a command fail or if a variable is empty + + echo -e "!!\n $app's script has encountered an error. Its execution was cancelled.\n!!" >&2 + + if type -t ynh_clean_setup > /dev/null; then # Check if the function exist in the app script. + ynh_clean_setup # Call the function to do specific cleaning for the app. + fi + + ynh_die # Exit with error status +} + +# Exit if an error occurs during the execution of the script. +# +# Stop immediatly the execution if an error occured or if a empty variable is used. +# The execution of the script is derivate to ynh_exit_properly function before exit. +# +# Usage: ynh_abort_if_errors +ynh_abort_if_errors () { + set -eu # Exit if a command fail, and if a variable is used unset. + trap ynh_exit_properly EXIT # Capturing exit signals on shell script +} + +# Install dependencies with a equivs control file +# +# usage: ynh_install_app_dependencies dep [dep [...]] +# | arg: dep - the package name to install in dependence +ynh_install_app_dependencies () { + dependencies=$@ + manifest_path="../manifest.json" + if [ ! -e "$manifest_path" ]; then + manifest_path="../settings/manifest.json" # Into the restore script, the manifest is not at the same place + fi + version=$(sudo python3 -c "import sys, json;print(json.load(open(\"$manifest_path\"))['version'])") # Retrieve the version number in the manifest file. + dep_app=${app//_/-} # Replace all '_' by '-' + + if ynh_package_is_installed "${dep_app}-ynh-deps"; then + echo "A package named ${dep_app}-ynh-deps is already installed" >&2 + else + cat > ./${dep_app}-ynh-deps.control << EOF # Make a control file for equivs-build +Section: misc +Priority: optional +Package: ${dep_app}-ynh-deps +Version: ${version} +Depends: ${dependencies// /, } +Architecture: all +Description: Fake package for ${app} (YunoHost app) dependencies + This meta-package is only responsible of installing its dependencies. +EOF + ynh_package_install_from_equivs ./${dep_app}-ynh-deps.control \ + || ynh_die "Unable to install dependencies" # Install the fake package and its dependencies + ynh_app_setting_set $app apt_dependencies $dependencies + fi +} + +# Remove fake package and its dependencies +# +# Dependencies will removed only if no other package need them. +# +# usage: ynh_remove_app_dependencies +ynh_remove_app_dependencies () { + dep_app=${app//_/-} # Replace all '_' by '-' + ynh_package_autoremove ${dep_app}-ynh-deps # Remove the fake package and its dependencies if they not still used. +} + +# Use logrotate to manage the logfile +# +# usage: ynh_use_logrotate [logfile] +# | arg: logfile - absolute path of logfile +# +# If no argument provided, a standard directory will be use. /var/log/${app} +# You can provide a path with the directory only or with the logfile. +# /parentdir/logdir/ +# /parentdir/logdir/logfile.log +# +# It's possible to use this helper several times, each config will added to same logrotate config file. +ynh_use_logrotate () { + if [ "$#" -gt 0 ]; then + if [ "$(echo ${1##*.})" == "log" ]; then # Keep only the extension to check if it's a logfile + logfile=$1 # In this case, focus logrotate on the logfile + else + logfile=$1/.log # Else, uses the directory and all logfile into it. + fi + else + logfile="/var/log/${app}/.log" # Without argument, use a defaut directory in /var/log + fi + cat > ./${app}-logrotate << EOF # Build a config file for logrotate +$logfile { + # Rotate if the logfile exceeds 100Mo + size 100M + # Keep 12 old log maximum + rotate 12 + # Compress the logs with gzip + compress + # Compress the log at the next cycle. So keep always 2 non compressed logs + delaycompress + # Copy and truncate the log to allow to continue write on it. Instead of move the log. + copytruncate + # Do not do an error if the log is missing + missingok + # Not rotate if the log is empty + notifempty + # Keep old logs in the same dir + noolddir +} +EOF + sudo mkdir -p $(dirname "$logfile") # Create the log directory, if not exist + cat ${app}-logrotate | sudo tee -a /etc/logrotate.d/$app > /dev/null # Append this config to the others for this app. If a config file already exist +} + +# Remove the app's logrotate config. +# +# usage: ynh_remove_logrotate +ynh_remove_logrotate () { + if [ -e "/etc/logrotate.d/$app" ]; then + sudo rm "/etc/logrotate.d/$app" + fi +} + +# Find a free port and return it +# +# example: port=$(ynh_find_port 8080) +# +# usage: ynh_find_port begin_port +# | arg: begin_port - port to start to search +ynh_find_port () { + port=$1 + test -n "$port" || ynh_die "The argument of ynh_find_port must be a valid port." + while netcat -z 127.0.0.1 $port # Check if the port is free + do + port=$((port+1)) # Else, pass to next port + done + echo $port +} + +# Create a system user +# +# usage: ynh_system_user_create user_name [home_dir] +# | arg: user_name - Name of the system user that will be create +# | arg: home_dir - Path of the home dir for the user. Usually the final path of the app. If this argument is omitted, the user will be created without home +ynh_system_user_create () { + if ! ynh_system_user_exists "$1" # Check if the user exists on the system + then # If the user doesn't exist + if [ $# -ge 2 ]; then # If a home dir is mentioned + user_home_dir="-d $2" + else + user_home_dir="--no-create-home" + fi + sudo useradd $user_home_dir --system --user-group $1 --shell /usr/sbin/nologin || ynh_die "Unable to create $1 system account" + fi +} + +# Delete a system user +# +# usage: ynh_system_user_delete user_name +# | arg: user_name - Name of the system user that will be create +ynh_system_user_delete () { + if ynh_system_user_exists "$1" # Check if the user exists on the system + then + echo "Remove the user $1" >&2 + sudo userdel $1 + else + echo "The user $1 was not found" >&2 + fi +} diff --git a/scripts/backup b/scripts/backup new file mode 100644 index 0000000..0aa0ce9 --- /dev/null +++ b/scripts/backup @@ -0,0 +1,56 @@ +#!/bin/bash + +#================================================= +# GENERIC STARTING +#================================================= +# MANAGE FAILURE OF THE SCRIPT +#================================================= + +# Exit on command errors and treat unset variables as an error +set -eu + +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +if [ ! -e _common.sh ]; then + # Rapatrie le fichier de fonctions si il n'est pas dans le dossier courant + sudo cp ../settings/scripts/_common.sh ./_common.sh + sudo chmod a+rx _common.sh +fi +source _common.sh +source /usr/share/yunohost/helpers + +#================================================= +# LOAD SETTINGS +#================================================= + +app=$YNH_APP_INSTANCE_NAME + +domain=$(ynh_app_setting_get $app domain) +final_path=$(ynh_app_setting_get $app final_path) +db_name=$(ynh_app_setting_get $app db_name) +db_pwd=$(ynh_app_setting_get "$app" mysqlpwd) + +#================================================= +# STANDARD BACKUP STEPS +#================================================= +# BACKUP OF THE MAIN DIR OF THE APP +#================================================= + +CHECK_SIZE "$final_path" +ynh_backup "$final_path" "sources" + +#================================================= +# BACKUP OF THE NGINX CONFIGURATION +#================================================= + +ynh_backup "/etc/nginx/conf.d/$domain.d/$app.conf" "nginx.conf" + +#================================================= +# BACKUP OF THE SQL BDD +#================================================= + +ynh_mysql_dump_db "$db_name" > dump.sql +CHECK_SIZE "dump.sql" +ynh_backup "dump.sql" "db.sql" diff --git a/scripts/install b/scripts/install new file mode 100644 index 0000000..725ed54 --- /dev/null +++ b/scripts/install @@ -0,0 +1,129 @@ +#!/bin/bash + +# https://github.com/YunoHost-Apps/wordpress_ynh/blob/code_refactoring/scripts/install + +#================================================= +# GENERIC STARTING +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +source _common.sh +source /usr/share/yunohost/helpers + +#================================================= +# MANAGE FAILURE OF THE SCRIPT +#================================================= + +ynh_abort_if_errors # Active trap pour arrêter le script si une erreur est détectée. + +#================================================= +# RETRIEVE ARGUMENTS FROM THE MANIFEST +#================================================= + +app=$YNH_APP_INSTANCE_NAME + +# Retrieve arguments +domain=$YNH_APP_ARG_DOMAIN +path_url=$YNH_APP_ARG_PATH +is_public=$YNH_APP_ARG_IS_PUBLIC +language=$YNH_APP_ARG_LANGUAGE + +path_url=$(ynh_normalize_url_path $path_url) # Vérifie et corrige la syntaxe du path. +CHECK_DOMAINPATH # Vérifie la disponibilité du path et du domaine. +CHECK_FINALPATH # Vérifie que le dossier de destination n'est pas déjà utilisé. + +sudo mkdir -p $final_path + +#================================================= +# STORE SETTINGS FROM MANIFEST +#================================================= + +ynh_app_setting_set $app domain $domain +ynh_app_setting_set $app path $path_url +ynh_app_setting_set $app is_public $is_public +ynh_app_setting_set $app language $language +ynh_app_setting_set $app final_path $final_path + +#================================================= +# CREATE A SQL BDD +#================================================= + +db_name=$(ynh_make_valid_dbid $app) +ynh_app_setting_set $app db_name $db_name +# $1 ownerdelabase, $2 namedelabase +ynh_mysql_generate_db $db_name $db_name + +# Charge les commandes sql communes à tous les scripts. +# mysql --debug-check -u $db_user -p$db_pwd $db_user < ../conf/sql/common.sql +ynh_mysql_connect_as $db_name $db_pwd $db_name < ../conf/sql/mytinytodo.sql + +#================================================= +# CREATE DEDICATED USER +#================================================= + +ynh_system_user_create $app # Créer un utilisateur système dédié à l'app mytinytodo + +#================================================= +# NGINX CONFIGURATION +#================================================= + +# Copie le fichier de config nginx +sudo cp ../conf/nginx.conf /etc/nginx/conf.d/$domain.d/$app.conf +# Modifie les variables dans le fichier de configuration nginx +#location directive +sudo sed -i "s@__PATHTOCHANGE__@$path_url@g" /etc/nginx/conf.d/$domain.d/$app.conf +#alias directive, il faut peut etre ajout un / apres final_path +sudo sed -i "s@__FINALPATH__@$final_path@g" /etc/nginx/conf.d/$domain.d/$app.conf + + +# verifier la valeur de $final_path pour moi il y a /var/www/mytinytodo +# la nom de la base et l'utilisateur de la base on la même valeur +# mise en place de la config de la base au niveau de mytinytodo + +sudo sed -i "s@__TODO_HOST__@localhost@g" ../conf/config.php +sudo sed -i "s@__TODO_DB__@$db_name@g" ../conf/config.php +sudo sed -i "s@__TODO_USER__@$db_name@g" ../conf/config.php +sudo sed -i "s@__TODO_PASSWORD__@$db_pwd@g" ../conf/config.php +sudo sed -i "s@__TODO_LANG__@$language@g" ../conf/config.php +sudo cp ../conf/config.php ../sources/www/db/config.php + + +# la partie copie des fichiers, mise en place final + +# avec le www +#sudo cp -r ../sources/www $final_path + +# sans le www +sudo cp -r ../sources/www/* $final_path + +#Verifier la syntaxe j'aimerai bien connaitre la valeur de ${user} +#sudo chown -hR "${user}:" "$DESTDIR" +#sudo chown -hR "www-data:" "$final_path" + +# Changement de droits pour que l'utilisateur puisse sauvegarder +# sa configuration dans config.php et les sessions dsans /tmp/sessions +sudo chmod o+w $final_path/db/config.php +sudo chmod o+w $final_path/tmp/sessions + +# je donne les droits a mytinytodo sur /var/www/mytinyto/* +sudo chown -R $app: $final_path + +#================================================= +# SETUP SSOWAT +#================================================= + +# 0 : pas d'acces publique +# 1 : acces publique autorise + +if [ $is_public -eq 0 ]; +then + # Retire l'accès public + ynh_app_setting_delete $app unprotected_uris +fi + +#================================================= +# RELOAD NGINX +#================================================= + +sudo systemctl reload nginx diff --git a/scripts/remove b/scripts/remove new file mode 100644 index 0000000..f43539c --- /dev/null +++ b/scripts/remove @@ -0,0 +1,53 @@ +#!/bin/bash + +#================================================= +# GENERIC STARTING +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +source _common.sh +source /usr/share/yunohost/helpers + +#================================================= +# LOAD SETTINGS +#================================================= + +app=$YNH_APP_INSTANCE_NAME + +domain=$(ynh_app_setting_get $app domain) +db_name=$(ynh_app_setting_get $app db_name) + +#================================================= +# STANDARD REMOVE +#================================================= +# REMOVE DEPENDENCIES +#================================================= + +ynh_remove_app_dependencies + +#================================================= +# REMOVE THE SQL BDD +#================================================= + +ynh_mysql_remove_db $db_name $db_name # Suppression de la base de donnée et de l'utilisateur associé. + +#================================================= +# REMOVE THE MAIN DIR OF THE APP +#================================================= + +SECURE_REMOVE '/var/www/$app' # Suppression du dossier de l'application + +#================================================= +# REMOVE THE NGINX CONFIGURATION +#================================================= + +REMOVE_NGINX_CONF # Suppression de la configuration nginx + +#================================================= +# GENERIC FINALISATION +#================================================= +# REMOVE DEDICATED USER +#================================================= + +ynh_system_user_delete $app diff --git a/scripts/restore b/scripts/restore new file mode 100644 index 0000000..949a79b --- /dev/null +++ b/scripts/restore @@ -0,0 +1,91 @@ +#!/bin/bash + +#================================================= +# GENERIC STARTING +#================================================= +# MANAGE FAILURE OF THE SCRIPT +#================================================= + +# Exit on command errors and treat unset variables as an error +set -eu + +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +if [ ! -e _common.sh ]; then + # Rapatrie le fichier de fonctions si il n'est pas dans le dossier courant + sudo cp ../settings/scripts/_common.sh ./_common.sh + sudo chmod a+rx _common.sh +fi +source _common.sh +source /usr/share/yunohost/helpers + +#================================================= +# LOAD SETTINGS +#================================================= + +app=$YNH_APP_INSTANCE_NAME + +domain=$(ynh_app_setting_get $app domain) +path_url=$(ynh_app_setting_get $app path) +is_public=$(ynh_app_setting_get $app is_public) +language=$(ynh_app_setting_get $app language) +final_path=$(ynh_app_setting_get $app final_path) +db_name=$(ynh_app_setting_get $app db_name) + +#================================================= +# CHECK IF THE APP CAN BE RESTORED +#================================================= + +sudo yunohost app checkurl "${domain}${path_url}" -a "$app" \ + || ynh_die "Path not available: ${domain}${path_url}" +test ! -d $final_path \ + || ynh_die "There is already a directory: $final_path " + +#================================================= +# STANDARD RESTORE STEPS +#================================================= +# RESTORE OF THE NGINX CONFIGURATION +#================================================= + +conf=/etc/nginx/conf.d/$domain.d/$app.conf +if [ -f $conf ]; then + ynh_die "There is already a nginx conf file at this path: $conf " +fi +sudo cp -a ./nginx.conf $conf + +#================================================= +# RESTORE OF THE MAIN DIR OF THE APP +#================================================= + +sudo cp -a ./sources/. $final_path + +#================================================= +# RESTORE OF THE SQL BDD +#================================================= + +db_pwd=$(ynh_app_setting_get $app mysqlpwd) +ynh_mysql_create_db $db_name $db_name $db_pwd +ynh_mysql_connect_as $db_name $db_pwd $db_name < ./db.sql + +#================================================= +# RECREATE OF THE DEDICATED USER +#================================================= + +ynh_system_user_create $app # Recreate the dedicated user, if not exist + +#================================================= +# RESTORE USER RIGHTS +#================================================= + +# Les fichiers appartiennent à l'user wordpress, pour permettre les mises à jour. +sudo chown -R $app: $final_path + +#================================================= +# GENERIC FINALISATION +#================================================= +# RELOAD NGINX +#================================================= + +sudo systemctl reload nginx diff --git a/sources/www/COPYRIGHT b/sources/www/COPYRIGHT new file mode 100644 index 0000000..6ea57f1 --- /dev/null +++ b/sources/www/COPYRIGHT @@ -0,0 +1,46 @@ +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or (at +your option) any later version. + +This program is distributed in the hope that it will be useful, but +WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY +or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with this program as the file LICENSE; if not, please see +http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt. + + +myTinyTodo +-------------- +Url: http://www.mytinytodo.net/ +Copyright: 2009,2010 Max Pozdeev +License: GPL version 2 (see LICENSE file) + + +myTinyTodo uses other works: + +jQuery +-------------- +Url: http://jquery.com/ +Copyright: 2009 John Resig +License: Dual licensed under the MIT and GPL version 2 licenses (see http://docs.jquery.com/License) + +jQuery UI +-------------- +Url: http://jqueryui.com/ +Copyright: 2009 jQuery UI Authors (see http://jqueryui.com/about) +License: Dual licensed under the MIT and GPL version 2 licenses (see http://jqueryui.com/about) + +Autocomplete - jQuery plugin +------------------------------ +Url: http://bassistance.de/jquery-plugins/jquery-plugin-autocomplete/ +Copyright: 2007 Dylan Verheul, Dan G. Switzer, Anjesh Tuladhar, Jörn Zaefferer +License: Dual licensed under the MIT and GPL licenses: + * http://www.opensource.org/licenses/mit-license.php + * http://www.gnu.org/licenses/gpl.html + + +This software contains images by 3d-parties. See file themes/default/images/COPYRIGHT for details. \ No newline at end of file diff --git a/sources/www/LICENSE b/sources/www/LICENSE new file mode 100755 index 0000000..d159169 --- /dev/null +++ b/sources/www/LICENSE @@ -0,0 +1,339 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc., + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Lesser General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along + with this program; if not, write to the Free Software Foundation, Inc., + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. diff --git a/sources/www/ajax.php b/sources/www/ajax.php new file mode 100644 index 0000000..498e4b5 --- /dev/null +++ b/sources/www/ajax.php @@ -0,0 +1,874 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +set_error_handler('myErrorHandler'); +set_exception_handler('myExceptionHandler'); + +require_once('./init.php'); + +$db = DBConnection::instance(); + +if(isset($_GET['loadLists'])) +{ + if($needAuth && !is_logged()) $sqlWhere = 'WHERE published=1'; + else $sqlWhere = ''; + $t = array(); + $t['total'] = 0; + $q = $db->dq("SELECT * FROM {$db->prefix}lists $sqlWhere ORDER BY ow ASC, id ASC"); + while($r = $q->fetch_assoc($q)) + { + $t['total']++; + $t['list'][] = prepareList($r); + } + jsonExit($t); +} +elseif(isset($_GET['loadTasks'])) +{ + stop_gpc($_GET); + $listId = (int)_get('list'); + check_read_access($listId); + + $sqlWhere = $inner = ''; + if($listId == -1) { + $userLists = getUserListsSimple(); + $sqlWhere .= " AND {$db->prefix}todolist.list_id IN (". implode(array_keys($userLists), ','). ") "; + } + else $sqlWhere .= " AND {$db->prefix}todolist.list_id=". $listId; + if(_get('compl') == 0) $sqlWhere .= ' AND compl=0'; + + $tag = trim(_get('t')); + if($tag != '') + { + $at = explode(',', $tag); + $tagIds = array(); + $tagExIds = array(); + foreach($at as $i=>$atv) { + $atv = trim($atv); + if($atv == '' || $atv == '^') continue; + if(substr($atv,0,1) == '^') { + $tagExIds[] = getTagId(substr($atv,1)); + } else { + $tagIds[] = getTagId($atv); + } + } + + if(sizeof($tagIds) > 1) { + $inner .= "INNER JOIN (SELECT task_id, COUNT(tag_id) AS c FROM {$db->prefix}tag2task WHERE list_id=$listId AND tag_id IN (". + implode(',',$tagIds). ") GROUP BY task_id) AS t2t ON id=t2t.task_id"; + $sqlWhere = " AND c=". sizeof($tagIds); //overwrite sqlWhere! + } + elseif($tagIds) { + $inner .= "INNER JOIN {$db->prefix}tag2task ON id=task_id"; + $sqlWhere .= " AND tag_id = ". $tagIds[0]; + } + + if($tagExIds) { + $sqlWhere .= " AND id NOT IN (SELECT DISTINCT task_id FROM {$db->prefix}tag2task WHERE list_id=$listId AND tag_id IN (". + implode(',',$tagExIds). "))"; //DISTINCT ? + } + } + + $s = trim(_get('s')); + if($s != '') $sqlWhere .= " AND (title LIKE ". $db->quoteForLike("%%%s%%",$s). " OR note LIKE ". $db->quoteForLike("%%%s%%",$s). ")"; + $sort = (int)_get('sort'); + $sqlSort = "ORDER BY compl ASC, "; + if($sort == 1) $sqlSort .= "prio DESC, ddn ASC, duedate ASC, ow ASC"; // byPrio + elseif($sort == 101) $sqlSort .= "prio ASC, ddn DESC, duedate DESC, ow DESC"; // byPrio (reverse) + elseif($sort == 2) $sqlSort .= "ddn ASC, duedate ASC, prio DESC, ow ASC"; // byDueDate + elseif($sort == 102) $sqlSort .= "ddn DESC, duedate DESC, prio ASC, ow DESC";// byDueDate (reverse) + elseif($sort == 3) $sqlSort .= "d_created ASC, prio DESC, ow ASC"; // byDateCreated + elseif($sort == 103) $sqlSort .= "d_created DESC, prio ASC, ow DESC"; // byDateCreated (reverse) + elseif($sort == 4) $sqlSort .= "d_edited ASC, prio DESC, ow ASC"; // byDateModified + elseif($sort == 104) $sqlSort .= "d_edited DESC, prio ASC, ow DESC"; // byDateModified (reverse) + else $sqlSort .= "ow ASC"; + + $t = array(); + $t['total'] = 0; + $t['list'] = array(); + $q = $db->dq("SELECT *, duedate IS NULL AS ddn FROM {$db->prefix}todolist $inner WHERE 1=1 $sqlWhere $sqlSort"); + while($r = $q->fetch_assoc($q)) + { + $t['total']++; + $t['list'][] = prepareTaskRow($r); + } + if(_get('setCompl') && have_write_access($listId)) { + $bitwise = (_get('compl') == 0) ? 'taskview & ~1' : 'taskview | 1'; + $db->dq("UPDATE {$db->prefix}lists SET taskview=$bitwise WHERE id=$listId"); + } + jsonExit($t); +} +elseif(isset($_GET['newTask'])) +{ + stop_gpc($_POST); + $listId = (int)_post('list'); + check_write_access($listId); + $t = array(); + $t['total'] = 0; + $title = trim(_post('title')); + $prio = 0; + $tags = ''; + if(Config::get('smartsyntax') != 0) + { + $a = parse_smartsyntax($title); + if($a === false) { + jsonExit($t); + } + $title = $a['title']; + $prio = $a['prio']; + $tags = $a['tags']; + } + if($title == '') { + jsonExit($t); + } + if(Config::get('autotag')) $tags .= ','._post('tag'); + $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}todolist WHERE list_id=$listId AND compl=0"); + $db->ex("BEGIN"); + $db->dq("INSERT INTO {$db->prefix}todolist (uuid,list_id,title,d_created,d_edited,ow,prio) VALUES (?,?,?,?,?,?,?)", + array(generateUUID(), $listId, $title, time(), time(), $ow, $prio) ); + $id = $db->last_insert_id(); + if($tags != '') + { + $aTags = prepareTags($tags); + if($aTags) { + addTaskTags($id, $aTags['ids'], $listId); + $db->ex("UPDATE {$db->prefix}todolist SET tags=?,tags_ids=? WHERE id=$id", array(implode(',',$aTags['tags']), implode(',',$aTags['ids']))); + } + } + $db->ex("COMMIT"); + $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=$id"); + $t['list'][] = prepareTaskRow($r); + $t['total'] = 1; + jsonExit($t); +} +elseif(isset($_GET['fullNewTask'])) +{ + stop_gpc($_POST); + $listId = (int)_post('list'); + check_write_access($listId); + $title = trim(_post('title')); + $note = str_replace("\r\n", "\n", trim(_post('note'))); + $prio = (int)_post('prio'); + if($prio < -1) $prio = -1; + elseif($prio > 2) $prio = 2; + $duedate = parse_duedate(trim(_post('duedate'))); + $t = array(); + $t['total'] = 0; + if($title == '') { + jsonExit($t); + } + $tags = trim(_post('tags')); + if(Config::get('autotag')) $tags .= ','._post('tag'); + $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}todolist WHERE list_id=$listId AND compl=0"); + $db->ex("BEGIN"); + $db->dq("INSERT INTO {$db->prefix}todolist (uuid,list_id,title,d_created,d_edited,ow,prio,note,duedate) VALUES(?,?,?,?,?,?,?,?,?)", + array(generateUUID(), $listId, $title, time(), time(), $ow, $prio, $note, $duedate) ); + $id = $db->last_insert_id(); + if($tags != '') + { + $aTags = prepareTags($tags); + if($aTags) { + addTaskTags($id, $aTags['ids'], $listId); + $db->ex("UPDATE {$db->prefix}todolist SET tags=?,tags_ids=? WHERE id=$id", array(implode(',',$aTags['tags']), implode(',',$aTags['ids']))); + } + } + $db->ex("COMMIT"); + $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=$id"); + $t['list'][] = prepareTaskRow($r); + $t['total'] = 1; + jsonExit($t); +} +elseif(isset($_GET['deleteTask'])) +{ + $id = (int)_post('id'); + $deleted = deleteTask($id); + $t = array(); + $t['total'] = $deleted; + $t['list'][] = array('id'=>$id); + jsonExit($t); +} +elseif(isset($_GET['completeTask'])) +{ + check_write_access(); + $id = (int)_post('id'); + $compl = _post('compl') ? 1 : 0; + $listId = (int)$db->sq("SELECT list_id FROM {$db->prefix}todolist WHERE id=$id"); + if($compl) $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}todolist WHERE list_id=$listId AND compl=1"); + else $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}todolist WHERE list_id=$listId AND compl=0"); + $dateCompleted = $compl ? time() : 0; + $db->dq("UPDATE {$db->prefix}todolist SET compl=$compl,ow=$ow,d_completed=?,d_edited=? WHERE id=$id", + array($dateCompleted, time()) ); + $t = array(); + $t['total'] = 1; + $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=$id"); + $t['list'][] = prepareTaskRow($r); + jsonExit($t); +} +elseif(isset($_GET['editNote'])) +{ + check_write_access(); + $id = (int)_post('id'); + stop_gpc($_POST); + $note = str_replace("\r\n", "\n", trim(_post('note'))); + $db->dq("UPDATE {$db->prefix}todolist SET note=?,d_edited=? WHERE id=$id", array($note, time()) ); + $t = array(); + $t['total'] = 1; + $t['list'][] = array('id'=>$id, 'note'=>nl2br(escapeTags($note)), 'noteText'=>(string)$note); + jsonExit($t); +} +elseif(isset($_GET['editTask'])) +{ + check_write_access(); + $id = (int)_post('id'); + stop_gpc($_POST); + $title = trim(_post('title')); + $note = str_replace("\r\n", "\n", trim(_post('note'))); + $prio = (int)_post('prio'); + if($prio < -1) $prio = -1; + elseif($prio > 2) $prio = 2; + $duedate = parse_duedate(trim(_post('duedate'))); + $t = array(); + $t['total'] = 0; + if($title == '') { + jsonExit($t); + } + $listId = $db->sq("SELECT list_id FROM {$db->prefix}todolist WHERE id=$id"); + $tags = trim(_post('tags')); + $db->ex("BEGIN"); + $db->ex("DELETE FROM {$db->prefix}tag2task WHERE task_id=$id"); + $aTags = prepareTags($tags); + if($aTags) { + $tags = implode(',', $aTags['tags']); + $tags_ids = implode(',',$aTags['ids']); + addTaskTags($id, $aTags['ids'], $listId); + } + $db->dq("UPDATE {$db->prefix}todolist SET title=?,note=?,prio=?,tags=?,tags_ids=?,duedate=?,d_edited=? WHERE id=$id", + array($title, $note, $prio, $tags, $tags_ids, $duedate, time()) ); + $db->ex("COMMIT"); + $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=$id"); + if($r) { + $t['list'][] = prepareTaskRow($r); + $t['total'] = 1; + } + jsonExit($t); +} +elseif(isset($_GET['changeOrder'])) +{ + check_write_access(); + stop_gpc($_POST); + $s = _post('order'); + parse_str($s, $order); + $t = array(); + $t['total'] = 0; + if($order) + { + $ad = array(); + foreach($order as $id=>$diff) { + $ad[(int)$diff][] = (int)$id; + } + $db->ex("BEGIN"); + foreach($ad as $diff=>$ids) { + if($diff >=0) $set = "ow=ow+".$diff; + else $set = "ow=ow-".abs($diff); + $db->dq("UPDATE {$db->prefix}todolist SET $set,d_edited=? WHERE id IN (".implode(',',$ids).")", array(time()) ); + } + $db->ex("COMMIT"); + $t['total'] = 1; + } + jsonExit($t); +} +elseif(isset($_POST['login'])) +{ + $t = array('logged' => 0); + if(!$needAuth) { + $t['disabled'] = 1; + jsonExit($t); + } + stop_gpc($_POST); + $password = _post('password'); + if($password == Config::get('password')) { + $t['logged'] = 1; + session_regenerate_id(1); + $_SESSION['logged'] = 1; + } + jsonExit($t); +} +elseif(isset($_POST['logout'])) +{ + unset($_SESSION['logged']); + $t = array('logged' => 0); + jsonExit($t); +} +elseif(isset($_GET['suggestTags'])) +{ + $listId = (int)_get('list'); + check_read_access($listId); + $begin = trim(_get('q')); + $limit = (int)_get('limit'); + if($limit<1) $limit = 8; + $q = $db->dq("SELECT name,id FROM {$db->prefix}tags INNER JOIN {$db->prefix}tag2task ON id=tag_id WHERE list_id=$listId AND name LIKE ". + $db->quoteForLike('%s%%',$begin) ." GROUP BY tag_id ORDER BY name LIMIT $limit"); + $s = ''; + while($r = $q->fetch_row()) { + $s .= "$r[0]|$r[1]\n"; + } + echo htmlarray($s); + exit; +} +elseif(isset($_GET['setPrio'])) +{ + check_write_access(); + $id = (int)$_GET['setPrio']; + $prio = (int)_get('prio'); + if($prio < -1) $prio = -1; + elseif($prio > 2) $prio = 2; + $db->ex("UPDATE {$db->prefix}todolist SET prio=$prio,d_edited=? WHERE id=$id", array(time()) ); + $t = array(); + $t['total'] = 1; + $t['list'][] = array('id'=>$id, 'prio'=>$prio); + jsonExit($t); +} +elseif(isset($_GET['tagCloud'])) +{ + $listId = (int)_get('list'); + check_read_access($listId); + + $q = $db->dq("SELECT name,tag_id,COUNT(tag_id) AS tags_count FROM {$db->prefix}tag2task INNER JOIN {$db->prefix}tags ON tag_id=id ". + "WHERE list_id=$listId GROUP BY (tag_id) ORDER BY tags_count ASC"); + $at = array(); + $ac = array(); + while($r = $q->fetch_assoc()) { + $at[] = array('name'=>$r['name'], 'id'=>$r['tag_id']); + $ac[] = $r['tags_count']; + } + + $t = array(); + $t['total'] = 0; + $count = sizeof($at); + if(!$count) { + jsonExit($t); + } + + $qmax = max($ac); + $qmin = min($ac); + if($count >= 10) $grades = 10; + else $grades = $count; + $step = ($qmax - $qmin)/$grades; + foreach($at as $i=>$tag) + { + $t['cloud'][] = array('tag'=>htmlarray($tag['name']), 'id'=>(int)$tag['id'], 'w'=> tag_size($qmin,$ac[$i],$step) ); + } + $t['total'] = $count; + jsonExit($t); +} +elseif(isset($_GET['addList'])) +{ + check_write_access(); + stop_gpc($_POST); + $t = array(); + $t['total'] = 0; + $name = str_replace(array('"',"'",'<','>','&'),array('','','','',''),trim(_post('name'))); + $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}lists"); + $db->dq("INSERT INTO {$db->prefix}lists (uuid,name,ow,d_created,d_edited) VALUES (?,?,?,?,?)", + array(generateUUID(), $name, $ow, time(), time()) ); + $id = $db->last_insert_id(); + $t['total'] = 1; + $r = $db->sqa("SELECT * FROM {$db->prefix}lists WHERE id=$id"); + $t['list'][] = prepareList($r); + jsonExit($t); +} +elseif(isset($_GET['renameList'])) +{ + check_write_access(); + stop_gpc($_POST); + $t = array(); + $t['total'] = 0; + $id = (int)_post('list'); + $name = str_replace(array('"',"'",'<','>','&'),array('','','','',''),trim(_post('name'))); + $db->dq("UPDATE {$db->prefix}lists SET name=?,d_edited=? WHERE id=$id", array($name, time()) ); + $t['total'] = $db->affected(); + $r = $db->sqa("SELECT * FROM {$db->prefix}lists WHERE id=$id"); + $t['list'][] = prepareList($r); + jsonExit($t); +} +elseif(isset($_GET['deleteList'])) +{ + check_write_access(); + stop_gpc($_POST); + $t = array(); + $t['total'] = 0; + $id = (int)_post('list'); + $db->ex("BEGIN"); + $db->ex("DELETE FROM {$db->prefix}lists WHERE id=$id"); + $t['total'] = $db->affected(); + if($t['total']) { + $db->ex("DELETE FROM {$db->prefix}tag2task WHERE list_id=$id"); + $db->ex("DELETE FROM {$db->prefix}todolist WHERE list_id=$id"); + } + $db->ex("COMMIT"); + jsonExit($t); +} +elseif(isset($_GET['setSort'])) +{ + check_write_access(); + $listId = (int)_post('list'); + $sort = (int)_post('sort'); + if($sort < 0 || $sort > 104) $sort = 0; + elseif($sort < 101 && $sort > 4) $sort = 0; + $db->ex("UPDATE {$db->prefix}lists SET sorting=$sort,d_edited=? WHERE id=$listId", array(time())); + jsonExit(array('total'=>1)); +} +elseif(isset($_GET['publishList'])) +{ + check_write_access(); + $listId = (int)_post('list'); + $publish = (int)_post('publish'); + $db->ex("UPDATE {$db->prefix}lists SET published=?,d_created=? WHERE id=$listId", array($publish ? 1 : 0, time())); + jsonExit(array('total'=>1)); +} +elseif(isset($_GET['moveTask'])) +{ + check_write_access(); + $id = (int)_post('id'); + $fromId = (int)_post('from'); + $toId = (int)_post('to'); + $result = moveTask($id, $toId); + $t = array('total' => $result ? 1 : 0); + if($fromId == -1 && $result && $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=$id")) { + $t['list'][] = prepareTaskRow($r); + } + jsonExit($t); +} +elseif(isset($_GET['changeListOrder'])) +{ + check_write_access(); + stop_gpc($_POST); + $order = (array)_post('order'); + $t = array(); + $t['total'] = 0; + if($order) + { + $a = array(); + $setCase = ''; + foreach($order as $ow=>$id) { + $id = (int)$id; + $a[] = $id; + $setCase .= "WHEN id=$id THEN $ow\n"; + } + $ids = implode($a, ','); + $db->dq("UPDATE {$db->prefix}lists SET d_edited=?, ow = CASE\n $setCase END WHERE id IN ($ids)", + array(time()) ); + $t['total'] = 1; + } + jsonExit($t); +} +elseif(isset($_GET['parseTaskStr'])) +{ + check_write_access(); + stop_gpc($_POST); + $t = array( + 'title' => trim(_post('title')), + 'prio' => 0, + 'tags' => '' + ); + if(Config::get('smartsyntax') != 0 && (false !== $a = parse_smartsyntax($t['title']))) + { + $t['title'] = $a['title']; + $t['prio'] = $a['prio']; + $t['tags'] = $a['tags']; + } + jsonExit($t); +} +elseif(isset($_GET['clearCompletedInList'])) +{ + check_write_access(); + stop_gpc($_POST); + $t = array(); + $t['total'] = 0; + $listId = (int)_post('list'); + $db->ex("BEGIN"); + $db->ex("DELETE FROM {$db->prefix}tag2task WHERE task_id IN (SELECT id FROM {$db->prefix}todolist WHERE list_id=? and compl=1)", array($listId)); + $db->ex("DELETE FROM {$db->prefix}todolist WHERE list_id=$listId and compl=1"); + $t['total'] = $db->affected(); + $db->ex("COMMIT"); + jsonExit($t); +} +elseif(isset($_GET['setShowNotesInList'])) +{ + check_write_access(); + $listId = (int)_post('list'); + $flag = (int)_post('shownotes'); + $bitwise = ($flag == 0) ? 'taskview & ~2' : 'taskview | 2'; + $db->dq("UPDATE {$db->prefix}lists SET taskview=$bitwise WHERE id=$listId"); + jsonExit(array('total'=>1)); +} +elseif(isset($_GET['setHideList'])) +{ + check_write_access(); + $listId = (int)_post('list'); + $flag = (int)_post('hide'); + $bitwise = ($flag == 0) ? 'taskview & ~4' : 'taskview | 4'; + $db->dq("UPDATE {$db->prefix}lists SET taskview=$bitwise WHERE id=$listId"); + jsonExit(array('total'=>1)); +} + + +################################################################################################### + +function prepareTaskRow($r) +{ + $lang = Lang::instance(); + $dueA = prepare_duedate($r['duedate']); + $formatCreatedInline = $formatCompletedInline = Config::get('dateformatshort'); + if(date('Y') != date('Y',$r['d_created'])) $formatCreatedInline = Config::get('dateformat2'); + if($r['d_completed'] && date('Y') != date('Y',$r['d_completed'])) $formatCompletedInline = Config::get('dateformat2'); + + $dCreated = timestampToDatetime($r['d_created']); + $dCompleted = $r['d_completed'] ? timestampToDatetime($r['d_completed']) : ''; + + return array( + 'id' => $r['id'], + 'title' => escapeTags($r['title']), + 'listId' => $r['list_id'], + 'date' => htmlarray($dCreated), + 'dateInt' => (int)$r['d_created'], + 'dateInline' => htmlarray(formatTime($formatCreatedInline, $r['d_created'])), + 'dateInlineTitle' => htmlarray(sprintf($lang->get('taskdate_inline_created'), $dCreated)), + 'dateEditedInt' => (int)$r['d_edited'], + 'dateCompleted' => htmlarray($dCompleted), + 'dateCompletedInline' => $r['d_completed'] ? htmlarray(formatTime($formatCompletedInline, $r['d_completed'])) : '', + 'dateCompletedInlineTitle' => htmlarray(sprintf($lang->get('taskdate_inline_completed'), $dCompleted)), + 'compl' => (int)$r['compl'], + 'prio' => $r['prio'], + 'note' => nl2br(escapeTags($r['note'])), + 'noteText' => (string)$r['note'], + 'ow' => (int)$r['ow'], + 'tags' => htmlarray($r['tags']), + 'tags_ids' => htmlarray($r['tags_ids']), + 'duedate' => $dueA['formatted'], + 'dueClass' => $dueA['class'], + 'dueStr' => htmlarray($r['compl'] && $dueA['timestamp'] ? formatTime($formatCompletedInline, $dueA['timestamp']) : $dueA['str']), + 'dueInt' => date2int($r['duedate']), + 'dueTitle' => htmlarray(sprintf($lang->get('taskdate_inline_duedate'), $dueA['formatted'])), + ); +} + +function check_read_access($listId = null) +{ + $db = DBConnection::instance(); + if(Config::get('password') == '') return true; + if(is_logged()) return true; + if($listId !== null) + { + $id = $db->sq("SELECT id FROM {$db->prefix}lists WHERE id=? AND published=1", array($listId)); + if($id) return; + } + jsonExit( array('total'=>0, 'list'=>array(), 'denied'=>1) ); +} + +function have_write_access($listId = null) +{ + if(is_readonly()) return false; + // check list exist + if($listId !== null) + { + $db = DBConnection::instance(); + $count = $db->sq("SELECT COUNT(*) FROM {$db->prefix}lists WHERE id=?", array($listId)); + if(!$count) return false; + } + return true; +} + +function check_write_access($listId = null) +{ + if(have_write_access($listId)) return; + jsonExit( array('total'=>0, 'list'=>array(), 'denied'=>1) ); +} + +function inputTaskParams() +{ + $a = array( + 'id' => _post('id'), + 'title'=> trim(_post('title')), + 'note' => str_replace("\r\n", "\n", trim(_post('note'))), + 'prio' => (int)_post('prio'), + 'duedate' => '', + 'tags' => trim(_post('tags')), + 'listId' => (int)_post('list'), + + ); + if($a['prio'] < -1) $a['prio'] = -1; + elseif($a['prio'] > 2) $a['prio'] = 2; + return $a; +} + +function prepareTags($tagsStr) +{ + $tags = explode(',', $tagsStr); + if(!$tags) return 0; + + $aTags = array('tags'=>array(), 'ids'=>array()); + foreach($tags as $tag) + { + $tag = str_replace(array('"',"'",'<','>','&','/','\\','^'),'',trim($tag)); + if($tag == '') continue; + + $aTag = getOrCreateTag($tag); + if($aTag && !in_array($aTag['id'], $aTags['ids'])) { + $aTags['tags'][] = $aTag['name']; + $aTags['ids'][] = $aTag['id']; + } + } + return $aTags; +} + +function getOrCreateTag($name) +{ + $db = DBConnection::instance(); + $tagId = $db->sq("SELECT id FROM {$db->prefix}tags WHERE name=?", array($name)); + if($tagId) return array('id'=>$tagId, 'name'=>$name); + + $db->ex("INSERT INTO {$db->prefix}tags (name) VALUES (?)", array($name)); + return array('id'=>$db->last_insert_id(), 'name'=>$name); +} + +function getTagId($tag) +{ + $db = DBConnection::instance(); + $id = $db->sq("SELECT id FROM {$db->prefix}tags WHERE name=?", array($tag)); + return $id ? $id : 0; +} + +function get_task_tags($id) +{ + $db = DBConnection::instance(); + $q = $db->dq("SELECT tag_id FROM {$db->prefix}tag2task WHERE task_id=?", $id); + $a = array(); + while($r = $q->fetch_row()) { + $a[] = $r[0]; + } + return $a; +} + + +function addTaskTags($taskId, $tagIds, $listId) +{ + $db = DBConnection::instance(); + if(!$tagIds) return; + foreach($tagIds as $tagId) + { + $db->ex("INSERT INTO {$db->prefix}tag2task (task_id,tag_id,list_id) VALUES (?,?,?)", array($taskId,$tagId,$listId)); + } +} + +function parse_smartsyntax($title) +{ + $a = array(); + if(!preg_match("|^(/([+-]{0,1}\d+)?/)?(.*?)(\s+/([^/]*)/$)?$|", $title, $m)) return false; + $a['prio'] = isset($m[2]) ? (int)$m[2] : 0; + $a['title'] = isset($m[3]) ? trim($m[3]) : ''; + $a['tags'] = isset($m[5]) ? trim($m[5]) : ''; + if($a['prio'] < -1) $a['prio'] = -1; + elseif($a['prio'] > 2) $a['prio'] = 2; + return $a; +} + +function tag_size($qmin, $q, $step) +{ + if($step == 0) return 1; + $v = ceil(($q - $qmin)/$step); + if($v == 0) return 0; + else return $v-1; + +} + +function parse_duedate($s) +{ + $df2 = Config::get('dateformat2'); + if(max((int)strpos($df2,'n'), (int)strpos($df2,'m')) > max((int)strpos($df2,'d'), (int)strpos($df2,'j'))) $formatDayFirst = true; + else $formatDayFirst = false; + + $y = $m = $d = 0; + if(preg_match("|^(\d+)-(\d+)-(\d+)\b|", $s, $ma)) { + $y = (int)$ma[1]; $m = (int)$ma[2]; $d = (int)$ma[3]; + } + elseif(preg_match("|^(\d+)\/(\d+)\/(\d+)\b|", $s, $ma)) + { + if($formatDayFirst) { + $d = (int)$ma[1]; $m = (int)$ma[2]; $y = (int)$ma[3]; + } else { + $m = (int)$ma[1]; $d = (int)$ma[2]; $y = (int)$ma[3]; + } + } + elseif(preg_match("|^(\d+)\.(\d+)\.(\d+)\b|", $s, $ma)) { + $d = (int)$ma[1]; $m = (int)$ma[2]; $y = (int)$ma[3]; + } + elseif(preg_match("|^(\d+)\.(\d+)\b|", $s, $ma)) { + $d = (int)$ma[1]; $m = (int)$ma[2]; + $a = explode(',', date('Y,m,d')); + if( $m<(int)$a[1] || ($m==(int)$a[1] && $d<(int)$a[2]) ) $y = (int)$a[0]+1; + else $y = (int)$a[0]; + } + elseif(preg_match("|^(\d+)\/(\d+)\b|", $s, $ma)) + { + if($formatDayFirst) { + $d = (int)$ma[1]; $m = (int)$ma[2]; + } else { + $m = (int)$ma[1]; $d = (int)$ma[2]; + } + $a = explode(',', date('Y,m,d')); + if( $m<(int)$a[1] || ($m==(int)$a[1] && $d<(int)$a[2]) ) $y = (int)$a[0]+1; + else $y = (int)$a[0]; + } + else return null; + if($y < 100) $y = 2000 + $y; + elseif($y < 1000 || $y > 2099) $y = 2000 + (int)substr((string)$y, -2); + if($m > 12) $m = 12; + $maxdays = daysInMonth($m,$y); + if($m < 10) $m = '0'.$m; + if($d > $maxdays) $d = $maxdays; + elseif($d < 10) $d = '0'.$d; + return "$y-$m-$d"; +} + +function prepare_duedate($duedate) +{ + $lang = Lang::instance(); + + $a = array( 'class'=>'', 'str'=>'', 'formatted'=>'', 'timestamp'=>0 ); + if($duedate == '') { + return $a; + } + $ad = explode('-', $duedate); + $at = explode('-', date('Y-m-d')); + $a['timestamp'] = mktime(0,0,0,$ad[1],$ad[2],$ad[0]); + $diff = mktime(0,0,0,$ad[1],$ad[2],$ad[0]) - mktime(0,0,0,$at[1],$at[2],$at[0]); + + if($diff < -604800 && $ad[0] == $at[0]) { $a['class'] = 'past'; $a['str'] = formatDate3(Config::get('dateformatshort'), (int)$ad[0], (int)$ad[1], (int)$ad[2], $lang); } + elseif($diff < -604800) { $a['class'] = 'past'; $a['str'] = formatDate3(Config::get('dateformat2'), (int)$ad[0], (int)$ad[1], (int)$ad[2], $lang); } + elseif($diff < -86400) { $a['class'] = 'past'; $a['str'] = sprintf($lang->get('daysago'),ceil(abs($diff)/86400)); } + elseif($diff < 0) { $a['class'] = 'past'; $a['str'] = $lang->get('yesterday'); } + elseif($diff < 86400) { $a['class'] = 'today'; $a['str'] = $lang->get('today'); } + elseif($diff < 172800) { $a['class'] = 'today'; $a['str'] = $lang->get('tomorrow'); } + elseif($diff < 691200) { $a['class'] = 'soon'; $a['str'] = sprintf($lang->get('indays'),ceil($diff/86400)); } + elseif($ad[0] == $at[0]) { $a['class'] = 'future'; $a['str'] = formatDate3(Config::get('dateformatshort'), (int)$ad[0], (int)$ad[1], (int)$ad[2], $lang); } + else { $a['class'] = 'future'; $a['str'] = formatDate3(Config::get('dateformat2'), (int)$ad[0], (int)$ad[1], (int)$ad[2], $lang); } + + $a['formatted'] = formatTime(Config::get('dateformat2'), $a['timestamp']); + + return $a; +} + +function date2int($d) +{ + if(!$d) return 33330000; + $ad = explode('-', $d); + $s = $ad[0]; + if(strlen($ad[1]) < 2) $s .= "0$ad[1]"; else $s .= $ad[1]; + if(strlen($ad[2]) < 2) $s .= "0$ad[2]"; else $s .= $ad[2]; + return (int)$s; +} + +function daysInMonth($m, $y=0) +{ + if($y == 0) $y = (int)date('Y'); + $a = array(1=>31,(($y-2000)%4?28:29),31,30,31,30,31,31,30,31,30,31); + if(isset($a[$m])) return $a[$m]; else return 0; +} + +function myErrorHandler($errno, $errstr, $errfile, $errline) +{ + if($errno==E_ERROR || $errno==E_CORE_ERROR || $errno==E_COMPILE_ERROR || $errno==E_USER_ERROR || $errno==E_PARSE) $error = 'Error'; + elseif($errno==E_WARNING || $errno==E_CORE_WARNING || $errno==E_COMPILE_WARNING || $errno==E_USER_WARNING || $errno==E_STRICT) { + if(error_reporting() & $errno) $error = 'Warning'; else return; + } + elseif($errno==E_NOTICE || $errno==E_USER_NOTICE) { + if(error_reporting() & $errno) $error = 'Notice'; else return; + } + elseif(defined('E_DEPRECATED') && ($errno==E_DEPRECATED || $errno==E_USER_DEPRECATED)) { # since 5.3.0 + if(error_reporting() & $errno) $error = 'Notice'; else return; + } + else $error = "Error ($errno)"; # here may be E_RECOVERABLE_ERROR + throw new Exception("$error: '$errstr' in $errfile:$errline", -1); +} + +function myExceptionHandler($e) +{ + try { // to avoid Exception thrown without a stack frame + if(-1 == $e->getCode()) { + echo $e->getMessage()."\n". $e->getTraceAsString(); + exit; + } + echo 'Exception: \''. $e->getMessage() .'\' in '. $e->getFile() .':'. $e->getLine(); //."\n". $e->getTraceAsString(); + } + catch(Exception $e) { + echo 'Exception in ExceptionHandler: \''. $e->getMessage() .'\' in '. $e->getFile() .':'. $e->getLine(); + } + exit; +} + +function deleteTask($id) +{ + check_write_access(); + $db = DBConnection::instance(); + $db->ex("BEGIN"); + $db->ex("DELETE FROM {$db->prefix}tag2task WHERE task_id=$id"); + //TODO: delete unused tags? + $db->dq("DELETE FROM {$db->prefix}todolist WHERE id=$id"); + $affected = $db->affected(); + $db->ex("COMMIT"); + return $affected; +} + +function moveTask($id, $listId) +{ + check_write_access(); + $db = DBConnection::instance(); + + // Check task exists and not in target list + $r = $db->sqa("SELECT * FROM {$db->prefix}todolist WHERE id=?", array($id)); + if(!$r || $listId == $r['list_id']) return false; + + // Check target list exists + if(!$db->sq("SELECT COUNT(*) FROM {$db->prefix}lists WHERE id=?", $listId)) + return false; + + $ow = 1 + (int)$db->sq("SELECT MAX(ow) FROM {$db->prefix}todolist WHERE list_id=? AND compl=?", array($listId, $r['compl']?1:0)); + + $db->ex("BEGIN"); + $db->ex("UPDATE {$db->prefix}tag2task SET list_id=? WHERE task_id=?", array($listId, $id)); + $db->dq("UPDATE {$db->prefix}todolist SET list_id=?, ow=?, d_edited=? WHERE id=?", array($listId, $ow, time(), $id)); + $db->ex("COMMIT"); + return true; +} + +function prepareList($row) +{ + $taskview = (int)$row['taskview']; + return array( + 'id' => $row['id'], + 'name' => htmlarray($row['name']), + 'sort' => (int)$row['sorting'], + 'published' => $row['published'] ? 1 :0, + 'showCompl' => $taskview & 1 ? 1 : 0, + 'showNotes' => $taskview & 2 ? 1 : 0, + 'hidden' => $taskview & 4 ? 1 : 0, + ); +} + +function getUserListsSimple() +{ + $db = DBConnection::instance(); + $a = array(); + $q = $db->dq("SELECT id,name FROM {$db->prefix}lists ORDER BY id ASC"); + while($r = $q->fetch_row()) { + $a[$r[0]] = $r[1]; + } + return $a; +} + +?> \ No newline at end of file diff --git a/sources/www/class.db.mysql.php b/sources/www/class.db.mysql.php new file mode 100644 index 0000000..45ed417 --- /dev/null +++ b/sources/www/class.db.mysql.php @@ -0,0 +1,172 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + + +class DatabaseResult_Mysql +{ + + var $parent; + var $q; + var $query; + var $rows = NULL; + var $affected = NULL; + var $prefix = ''; + + function __construct($query, &$h, $resultless = 0) + { + $this->parent = $h; + $this->query = $query; + + $this->q = mysql_query($query, $this->parent->dbh); + + if(!$this->q) + { + throw new Exception($this->parent->error()); + } + } + + function affected() + { + if(is_null($this->affected)) + { + $this->affected = mysql_affected_rows($this->parent->dbh); + } + return $this->affected; + } + + function fetch_row() + { + return mysql_fetch_row($this->q); + } + + function fetch_assoc() + { + return mysql_fetch_assoc($this->q); + } + + function rows() + { + if (!is_null($this -> rows)) return $this->rows; + $this->rows = mysql_num_rows($this->q); + return $this->rows; + } +} + +class Database_Mysql +{ + var $dbh; + var $error_str; + + function __construct() + { + } + + function connect($host, $user, $pass, $db) + { + if(!$this->dbh = @mysql_connect($host,$user,$pass)) + { + throw new Exception(mysql_error()); + } + if( @!mysql_select_db($db, $this->dbh) ) + { + throw new Exception($this->error()); + } + return true; + } + + function last_insert_id() + { + return mysql_insert_id($this->dbh); + } + + function error() + { + return mysql_error($this->dbh); + } + + function sq($query, $p = NULL) + { + $q = $this->_dq($query, $p); + + if($q->rows()) $res = $q->fetch_row(); + else return NULL; + + if(sizeof($res) > 1) return $res; + else return $res[0]; + } + + function sqa($query, $p = NULL) + { + $q = $this->_dq($query, $p); + + if($q->rows()) $res = $q->fetch_assoc(); + else return NULL; + + if(sizeof($res) > 1) return $res; + else return $res[0]; + } + + function dq($query, $p = NULL) + { + return $this->_dq($query, $p); + } + + function ex($query, $p = NULL) + { + return $this->_dq($query, $p, 1); + } + + private function _dq($query, $p = NULL, $resultless = 0) + { + if(!isset($p)) $p = array(); + elseif(!is_array($p)) $p = array($p); + + $m = explode('?', $query); + + if(sizeof($p)>0) + { + if(sizeof($m)< sizeof($p)+1) { + throw new Exception("params to set MORE than query params"); + } + if(sizeof($m)> sizeof($p)+1) { + throw new Exception("params to set LESS than query params"); + } + $query = ""; + for($i=0; $iquote($p[$i])); + } + $query .= $m[$i]; + } + return new DatabaseResult_Mysql($query, $this, $resultless); + } + + function affected() + { + return mysql_affected_rows($this->dbh); + } + + function quote($s) + { + return '\''. addslashes($s). '\''; + } + + function quoteForLike($format, $s) + { + $s = str_replace(array('%','_'), array('\%','\_'), addslashes($s)); + return '\''. sprintf($format, $s). '\''; + } + + function table_exists($table) + { + $table = addslashes($table); + $q = mysql_query("SELECT 1 FROM `$table` WHERE 1=0", $this->dbh); + if($q === false) return false; + else return true; + } +} + +?> \ No newline at end of file diff --git a/sources/www/class.db.sqlite3.php b/sources/www/class.db.sqlite3.php new file mode 100644 index 0000000..f6a8acc --- /dev/null +++ b/sources/www/class.db.sqlite3.php @@ -0,0 +1,162 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +class DatabaseResult_Sqlite3 +{ + private $parent; + private $q; + var $query; + var $prefix; + + function __construct($query, &$h, $resultless = 0) + { + $this->parent = $h; + $this->parent->lastQuery = $this->query = $query; + + if($resultless) + { + $r = $this->parent->dbh->exec($query); + if($r === false) { + $ei = $this->parent->dbh->errorInfo(); + throw new Exception($ei[2]); + } + $this->parent->affected = $r; + } + else + { + $this->q = $this->parent->dbh->query($query); + if(!$this->q) { + $ei = $this->parent->dbh->errorInfo(); + throw new Exception($ei[2]); + } + $this->parent->affected = $this->q->rowCount(); + } + } + + function fetch_row() + { + return $this->q->fetch(PDO::FETCH_NUM); + } + + function fetch_assoc() + { + return $this->q->fetch(PDO::FETCH_ASSOC); + } + +} + +class Database_Sqlite3 +{ + var $dbh; + var $affected = null; + var $lastQuery; + + function __construct() + { + } + + function connect($filename) + { + try { + $this->dbh = new PDO("sqlite:$filename"); + } + catch(PDOException $e) { + throw new Exception($e->getMessage()); + } + return true; + } + + function sq($query, $p = NULL) + { + $q = $this->_dq($query, $p); + + $res = $q->fetch_row(); + if($res === false) return NULL; + + if(sizeof($res) > 1) return $res; + else return $res[0]; + } + + function sqa($query, $p = NULL) + { + $q = $this->_dq($query, $p); + + $res = $q->fetch_assoc(); + if($res === false) return NULL; + + if(sizeof($res) > 1) return $res; + else return $res[0]; + } + + function dq($query, $p = NULL) + { + return $this->_dq($query, $p); + } + + /* + for resultless queries like INSERT,UPDATE + */ + function ex($query, $p = NULL) + { + return $this->_dq($query, $p, 1); + } + + private function _dq($query, $p = NULL, $resultless = 0) + { + if(!isset($p)) $p = array(); + elseif(!is_array($p)) $p = array($p); + + $m = explode('?', $query); + + if(sizeof($p)>0) + { + if(sizeof($m)< sizeof($p)+1) { + throw new Exception("params to set MORE than query params"); + } + if(sizeof($m)> sizeof($p)+1) { + throw new Exception("params to set LESS than query params"); + } + $query = ""; + for($i=0; $iquote($p[$i])); + } + $query .= $m[$i]; + } + return new DatabaseResult_Sqlite3($query, $this, $resultless); + } + + function affected() + { + return $this->affected; + } + + function quote($s) + { + return $this->dbh->quote($s); + } + + function quoteForLike($format, $s) + { + $s = str_replace(array('\\','%','_'), array('\\\\','\%','\_'), $s); + return $this->dbh->quote(sprintf($format, $s)). " ESCAPE '\'"; + } + + function last_insert_id() + { + return $this->dbh->lastInsertId(); + } + + function table_exists($table) + { + $table = $this->dbh->quote($table); + $q = $this->dbh->query("SELECT 1 FROM $table WHERE 1=0"); + if($q === false) return false; + else return true; + } +} + +?> \ No newline at end of file diff --git a/sources/www/common.php b/sources/www/common.php new file mode 100644 index 0000000..e066fee --- /dev/null +++ b/sources/www/common.php @@ -0,0 +1,208 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +function htmlarray($a, $exclude=null) +{ + htmlarray_ref($a, $exclude); + return $a; +} + +function htmlarray_ref(&$a, $exclude=null) +{ + if(!$a) return; + if(!is_array($a)) { + $a = htmlspecialchars($a); + return; + } + reset($a); + if($exclude && !is_array($exclude)) $exclude = array($exclude); + foreach($a as $k=>$v) + { + if(is_array($v)) $a[$k] = htmlarray($v, $exclude); + elseif(!$exclude) $a[$k] = htmlspecialchars($v); + elseif(!in_array($k, $exclude)) $a[$k] = htmlspecialchars($v); + } + return; +} + +function stop_gpc(&$arr) +{ + if (!is_array($arr)) return 1; + + if (!get_magic_quotes_gpc()) return 1; + reset($arr); + foreach($arr as $k=>$v) + { + if(is_array($arr[$k])) stop_gpc($arr[$k]); + elseif(is_string($arr[$k])) $arr[$k] = stripslashes($v); + } + + return 1; +} +function _post($param,$defvalue = '') +{ + if(!isset($_POST[$param])) { + return $defvalue; + } + else { + return $_POST[$param]; + } +} + +function _get($param,$defvalue = '') +{ + if(!isset($_GET[$param])) { + return $defvalue; + } + else { + return $_GET[$param]; + } +} + +class Config +{ + public static $params = array( + 'db' => array('default'=>'sqlite', 'type'=>'s'), + 'mysql.host' => array('default'=>'localhost', 'type'=>'s'), + 'mysql.db' => array('default'=>'mytinytodo', 'type'=>'s'), + 'mysql.user' => array('default'=>'user', 'type'=>'s'), + 'mysql.password' => array('default'=>'', 'type'=>'s'), + 'prefix' => array('default'=>'', 'type'=>'s'), + 'url' => array('default'=>'', 'type'=>'s'), + 'mtt_url' => array('default'=>'', 'type'=>'s'), + 'title' => array('default'=>'', 'type'=>'s'), + 'lang' => array('default'=>'en', 'type'=>'s'), + 'password' => array('default'=>'', 'type'=>'s'), + 'smartsyntax' => array('default'=>1, 'type'=>'i'), + 'timezone' => array('default'=>'UTC', 'type'=>'s'), + 'autotag' => array('default'=>1, 'type'=>'i'), + 'duedateformat' => array('default'=>1, 'type'=>'i'), + 'firstdayofweek' => array('default'=>1, 'type'=>'i'), + 'session' => array('default'=>'files', 'type'=>'s', 'options'=>array('files','default')), + 'clock' => array('default'=>24, 'type'=>'i', 'options'=>array(12,24)), + 'dateformat' => array('default'=>'j M Y', 'type'=>'s'), + 'dateformat2' => array('default'=>'n/j/y', 'type'=>'s'), + 'dateformatshort' => array('default'=>'j M', 'type'=>'s'), + 'template' => array('default'=>'default', 'type'=>'s'), + 'showdate' => array('default'=>0, 'type'=>'i'), + ); + + public static $config; + + public static function loadConfig($config) + { + self::$config = $config; + } + + public static function get($key) + { + if(isset(self::$config[$key])) return self::$config[$key]; + elseif(isset(self::$params[$key])) return self::$params[$key]['default']; + else return null; + } + + public static function set($key, $value) + { + self::$config[$key] = $value; + } + + public static function save() + { + $s = ''; + foreach(self::$params as $param=>$v) + { + if(!isset(self::$config[$param])) $val = $v['default']; + elseif(isset($v['options']) && !in_array(self::$config[$param], $v['options'])) $val = $v['default']; + else $val = self::$config[$param]; + if($v['type']=='i') { + $s .= "\$config['$param'] = ".(int)$val.";\n"; + } + else { + $s .= "\$config['$param'] = '".str_replace(array("\\","'"),array("\\\\","\\'"),$val)."';\n"; + } + } + $f = fopen(MTTPATH. 'db/config.php', 'w'); + if($f === false) throw new Exception("Error while saving config file"); + fwrite($f, ""); + fclose($f); + } +} + +function formatDate3($format, $ay, $am, $ad, $lang) +{ + # F - month long, M - month short + # m - month 2-digit, n - month 1-digit + # d - day 2-digit, j - day 1-digit + $ml = $lang->get('months_long'); + $ms = $lang->get('months_short'); + $Y = $ay; + $y = $Y < 2010 ? '0'.($Y-2000) : $Y-2000; + $n = $am; + $m = $n < 10 ? '0'.$n : $n; + $F = $ml[$am-1]; + $M = $ms[$am-1]; + $j = $ad; + $d = $j < 10 ? '0'.$j : $j; + return strtr($format, array('Y'=>$Y, 'y'=>$y, 'F'=>$F, 'M'=>$M, 'n'=>$n, 'm'=>$m, 'd'=>$d, 'j'=>$j)); +} + +function url_dir($url) +{ + if(false !== $p = strpos($url, '?')) $url = substr($url,0,$p); # to avoid parse errors on strange query strings + $p = parse_url($url, PHP_URL_PATH); + if($p == '') return '/'; + if(substr($p,-1) == '/') return $p; + if(false !== $pos = strrpos($p,'/')) return substr($p,0,$pos+1); + return '/'; +} + +function escapeTags($s) +{ + $c1 = chr(1); + $c2 = chr(2); + $s = preg_replace("~([\s\S]*?)~i", "${c1}b${c2}\$1${c1}/b${c2}", $s); + $s = preg_replace("~([\s\S]*?)~i", "${c1}i${c2}\$1${c1}/i${c2}", $s); + $s = preg_replace("~([\s\S]*?)~i", "${c1}u${c2}\$1${c1}/u${c2}", $s); + $s = preg_replace("~([\s\S]*?)~i", "${c1}s${c2}\$1${c1}/s${c2}", $s); + $s = str_replace(array($c1, $c2), array('<','>'), htmlspecialchars($s)); + return $s; +} + +/* found in comments on http://www.php.net/manual/en/function.uniqid.php#94959 */ +function generateUUID() +{ + return sprintf('%04x%04x-%04x-%04x-%04x-%04x%04x%04x', + mt_rand(0, 0xffff), mt_rand(0, 0xffff), mt_rand(0, 0xffff), + mt_rand(0, 0x0fff) | 0x4000, + mt_rand(0, 0x3fff) | 0x8000, + mt_rand(0, 0xffff), mt_rand(0, 0xffff), mt_rand(0, 0xffff) + ); +} + +class DBConnection +{ + protected static $instance; + + public static function init($instance) + { + self::$instance = $instance; + return $instance; + } + + public static function instance() + { + if (!isset(self::$instance)) { + //$c = __CLASS__; + $c = 'DBConnection'; + self::$instance = new $c; + } + return self::$instance; + } +} + +?> \ No newline at end of file diff --git a/sources/www/db/.htaccess b/sources/www/db/.htaccess new file mode 100644 index 0000000..3418e55 --- /dev/null +++ b/sources/www/db/.htaccess @@ -0,0 +1 @@ +deny from all \ No newline at end of file diff --git a/sources/www/export.php b/sources/www/export.php new file mode 100644 index 0000000..d10a454 --- /dev/null +++ b/sources/www/export.php @@ -0,0 +1,152 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +//$dontStartSession = 1; +require_once('./init.php'); + +$onlyPublishedList = false; +if(!have_write_access()) $onlyPublishedList = true; + +$listId = (int)_get('list'); +$listData = $db->sqa("SELECT * FROM {$db->prefix}lists WHERE id=$listId ". ($onlyPublishedList ? "AND published=1" : "") ); +if(!$listData) { + die("No such list or access denied"); +} + +$sqlSort = "ORDER BY compl ASC, "; +if($listData['sorting'] == 1) $sqlSort .= "prio DESC, ddn ASC, duedate ASC, ow ASC"; +elseif($listData['sorting'] == 2) $sqlSort .= "ddn ASC, duedate ASC, prio DESC, ow ASC"; +else $sqlSort .= "ow ASC"; + +$data = array(); +$q = $db->dq("SELECT *, duedate IS NULL AS ddn FROM {$db->prefix}todolist WHERE list_id=$listId $sqlSort"); +while($r = $q->fetch_assoc($q)) +{ + $data[] = $r; +} + +$format = _get('format'); + +if($format == 'ical') printICal($listData, $data); +else printCSV($listData, $data); + + +function have_write_access() +{ + if(Config::get('password') == '') return true; + if(is_logged()) return true; + return false; +} + + +function printCSV($listData, $data) +{ + $s = /*chr(0xEF).chr(0xBB).chr(0xBF).*/ "Completed,Priority,Task,Notes,Tags,Due,DateCreated,DateCompleted\n"; + foreach($data as $r) + { + $s .= ($r['compl']?'1':'0'). ','. $r['prio']. ','. escape_csv($r['title']). ','. + escape_csv($r['note']). ','. escape_csv($r['tags']). ','. $r['duedate']. + ','. date('Y-m-d H:i:s O',$r['d_created']). ','. ($r['d_completed'] ? date('Y-m-d H:i:s O',$r['d_completed']) :''). "\n"; + } + header('Content-type: text/csv; charset=utf-8'); + header('Content-disposition: attachment; filename=list_'.$listData['id'].'.csv'); + print $s; +} + +function escape_csv($v) +{ + return '"'.str_replace('"', '""', $v).'"'; +} + +function printICal($listData, $data) +{ + $mttToIcalPrio = array("1" => 5, "2" => 1); + $s = "BEGIN:VCALENDAR\r\nVERSION:2.0\r\nMETHOD:PUBLISH\r\nCALSCALE:GREGORIAN\r\nPRODID:-//myTinyTodo//iCalendar Export v1.4//EN\r\n". + "X-WR-CALNAME:". $listData['name']. "\r\nX-MTT-TIMEZONE:".Config::get('timezone')."\r\n"; + # to-do + foreach($data as $r) + { + $a = array(); + $a[] = "BEGIN:VTODO"; + $a[] = "UID:". $r['uuid']; + $a[] = "CREATED:". gmdate('Ymd\THis\Z', $r['d_created']); + $a[] = "DTSTAMP:". gmdate('Ymd\THis\Z', $r['d_edited']); + $a[] = "LAST-MODIFIED:". gmdate('Ymd\THis\Z', $r['d_edited']); + $a[] = utf8chunks("SUMMARY:". $r['title']); + if($r['duedate']) { + $dda = explode('-', $r['duedate']); + $a[] = "DUE;VALUE=DATE:".sprintf("%u%02u%02u", $dda[0], $dda[1], $dda[2]); + } + # Apple's iCal priorities: low-9, medium-5, high-1 + if($r['prio'] > 0 && isset($mttToIcalPrio[$r['prio']])) $a[] = "PRIORITY:". $mttToIcalPrio[$r['prio']]; + $a[] = "X-MTT-PRIORITY:". $r['prio']; + + $descr = array(); + if($r['tags'] != '') $descr[] = Lang::instance()->get('tags'). ": ". str_replace(',', ', ', $r['tags']); + if($r['note'] != '') $descr[] = Lang::instance()->get('note'). ": ". $r['note']; + if($descr) $a[] = utf8chunks("DESCRIPTION:". str_replace("\n", '\\n', implode("\n",$descr))); + + if($r['compl']) { + $a[] = "STATUS:COMPLETED"; #used in Sunbird + $a[] = "COMPLETED:". gmdate('Ymd\THis\Z', $r['d_completed']); + #$a[] = "PERCENT-COMPLETE:100"; #used in Sunbird + } + if($r['tags'] != '') $a[] = utf8chunks("X-MTT-TAGS:". $r['tags']); + $a[] = "END:VTODO\r\n"; + $s .= implode("\r\n", $a); + } + # events + foreach($data as $r) + { + if(!$r['duedate'] || $r['compl']) continue; # skip tasks completed and without duedate + $a = array(); + $a[] = "BEGIN:VEVENT"; + $a[] = "UID:_". $r['uuid']; # do not duplicate VTODO UID + $a[] = "CREATED:". gmdate('Ymd\THis\Z', $r['d_created']); + $a[] = "DTSTAMP:". gmdate('Ymd\THis\Z', $r['d_edited']); + $a[] = "LAST-MODIFIED:". gmdate('Ymd\THis\Z', $r['d_edited']); + $a[] = utf8chunks("SUMMARY:". $r['title']); + if($r['prio'] > 0 && isset($mttToIcalPrio[$r['prio']])) $a[] = "PRIORITY:". $mttToIcalPrio[$r['prio']]; + $dda = explode('-', $r['duedate']); + $a[] = "DTSTART;VALUE=DATE:".sprintf("%u%02u%02u", $dda[0], $dda[1], $dda[2]); + $a[] = "DTEND;VALUE=DATE:".date('Ymd', mktime(1,1,1,$dda[1],$dda[2],$dda[0]) + 86400); + $descr = array(); + if($r['tags'] != '') $descr[] = Lang::instance()->get('tags'). ": ". str_replace(',', ', ', $r['tags']); + if($r['note'] != '') $descr[] = Lang::instance()->get('note'). ": ". $r['note']; + if($descr) $a[] = utf8chunks("DESCRIPTION:". str_replace("\n", '\\n', implode("\n",$descr))); + $a[] = "END:VEVENT\r\n"; + $s .= implode("\r\n", $a); + } + $s .= "END:VCALENDAR\r\n"; + header('Content-type: text/calendar; charset=utf-8'); + header('Content-disposition: attachment; filename=list_'.$listData['id'].'.ics'); + print $s; +} + +function utf8chunks($text, $chunklen=75, $delimiter="\r\n\t") +{ + if($text == '') return ''; + preg_match_all('/./u', $text, $m); + $chars = $m[0]; + $a = array(); + $s = ''; + $max = count($chars); + for($i=0; $i<$max; $i++) + { + $ch = $chars[$i]; + if(strlen($s) + strlen($ch) > $chunklen) { # line should be not more than $chunklen bytes + $a[] = $s; + $s = $ch; + } + else $s .= $ch; + } + if($s != '') $a[] = $s; + return implode($delimiter, $a); +} + +?> \ No newline at end of file diff --git a/sources/www/feed.php b/sources/www/feed.php new file mode 100644 index 0000000..ed8ec03 --- /dev/null +++ b/sources/www/feed.php @@ -0,0 +1,98 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +$dontStartSession = 1; +require_once('./init.php'); + +$lang = Lang::instance(); + +$listId = (int)_get('list'); + +$listData = $db->sqa("SELECT * FROM {$db->prefix}lists WHERE id=$listId"); +if($needAuth && (!$listData || !$listData['published'])) { + die("Access denied!
List is not published."); +} +if(!$listData) { + die("No such list"); +} + +$feedType = _get('feed'); +$sqlWhere = ''; +if($feedType == 'completed') { + $listData['_uid_field'] = 'd_completed'; + $listData['_feed_descr'] = $lang->get('feed_completed_tasks'); + $sqlWhere = 'AND compl=1'; +} +elseif($feedType == 'modified') { + $listData['_uid_field'] = 'd_edited'; + $listData['_feed_descr'] = $lang->get('feed_modified_tasks'); +} +elseif($feedType == 'current') { + $listData['_uid_field'] = 'd_created'; + $listData['_feed_descr'] = $lang->get('feed_new_tasks'); + $sqlWhere = 'AND compl=0'; +} +else { + $listData['_uid_field'] = 'd_created'; + $listData['_feed_descr'] = $lang->get('feed_new_tasks'); +} + +$listData['_feed_title'] = sprintf($lang->get('feed_title'), $listData['name']) . ' - '. $listData['_feed_descr']; +htmlarray_ref($listData); + +$data = array(); +$q = $db->dq("SELECT * FROM {$db->prefix}todolist WHERE list_id=$listId $sqlWhere ORDER BY ". $listData['_uid_field'] ." DESC LIMIT 100"); +while($r = $q->fetch_assoc($q)) +{ + if($r['prio'] > 0) $r['prio'] = '+'.$r['prio']; + $a = array(); + if($r['prio']) $a[] = $lang->get('priority'). ": $r[prio]"; + if($r['duedate'] != '') { + $ad = explode('-', $r['duedate']); + $a[] = $lang->get('due'). ": ".formatDate3(Config::get('dateformat'), (int)$ad[0], (int)$ad[1], (int)$ad[2], $lang); + } + if($r['tags'] != '') $a[] = $lang->get('tags'). ": ". str_replace(',', ', ', $r['tags']); + if($r['compl']) $a[] = $lang->get('taskdate_completed'). ": ". timestampToDatetime($r['d_completed']); + $r['title'] = strip_tags($r['title']); + $r['note'] = escapeTags($r['note']); + $r['_descr'] = nl2br($r['note']). ($a && $r['note']!='' ? "

" : ""). implode("
", htmlarray($a)); + $data[] = $r; +} + +printRss($listData, $data); + + +function printRss($listData, $data) +{ + $link = get_mttinfo('url'). "?list=". $listData['id']; + $buildDate = gmdate('r'); + + $s = "\n\n\n". + "$listData[_feed_title]\n$link\n$listData[_feed_descr]\n". + "$buildDate\n\n"; + + foreach($data as $v) + { + $d = gmdate('r', $v[$listData['_uid_field']]); + $guid = $listData['id'].'-'.$v['id'].'-'.$v[$listData['_uid_field']]; + + $s .= "\n<![CDATA[". str_replace("]]>", "]]]]><![CDATA[>", $v['title']). "]]>\n". + "$link\n". + "$d\n". + "\n". + "$guid\n". + "\n"; + } + + $s .= "\n"; + + header("Content-type: text/xml; charset=utf-8"); + print $s; +} + +?> \ No newline at end of file diff --git a/sources/www/index.php b/sources/www/index.php new file mode 100644 index 0000000..a53aa78 --- /dev/null +++ b/sources/www/index.php @@ -0,0 +1,20 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +require_once('./init.php'); + +$lang = Lang::instance(); + +if($lang->rtl()) Config::set('rtl', 1); + +if(!is_int(Config::get('firstdayofweek')) || Config::get('firstdayofweek')<0 || Config::get('firstdayofweek')>6) Config::set('firstdayofweek', 1); + +define('TEMPLATEPATH', MTTPATH. 'themes/'.Config::get('template').'/'); + +require(TEMPLATEPATH. 'index.php'); + +?> \ No newline at end of file diff --git a/sources/www/init.php b/sources/www/init.php new file mode 100644 index 0000000..12db713 --- /dev/null +++ b/sources/www/init.php @@ -0,0 +1,161 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +if(!defined('MTTPATH')) define('MTTPATH', dirname(__FILE__) .'/'); + +require_once(MTTPATH. 'common.php'); +require_once(MTTPATH. 'db/config.php'); + +ini_set('display_errors', 'On'); + +if(!isset($config)) global $config; +Config::loadConfig($config); +unset($config); + +date_default_timezone_set(Config::get('timezone')); + +# MySQL Database Connection +if(Config::get('db') == 'mysql') +{ + require_once(MTTPATH. 'class.db.mysql.php'); + $db = DBConnection::init(new Database_Mysql); + $db->connect(Config::get('mysql.host'), Config::get('mysql.user'), Config::get('mysql.password'), Config::get('mysql.db')); + $db->dq("SET NAMES utf8"); +} + +# SQLite3 (pdo_sqlite) +elseif(Config::get('db') == 'sqlite') +{ + require_once(MTTPATH. 'class.db.sqlite3.php'); + $db = DBConnection::init(new Database_Sqlite3); + $db->connect(MTTPATH. 'db/todolist.db'); +} +else { + # It seems not installed + die("Not installed. Run setup.php first."); +} +$db->prefix = Config::get('prefix'); + +//User can override language setting by cookies +if(isset($_COOKIE['lang']) && preg_match("/^[a-z-]+$/i", $_COOKIE['lang']) && file_exists('lang/'. $_COOKIE['lang']. '.php')) { + Config::set('lang', $_COOKIE['lang']); +} + +require_once(MTTPATH. 'lang/class.default.php'); +require_once(MTTPATH. 'lang/'.Config::get('lang').'.php'); + +$_mttinfo = array(); + +$needAuth = (Config::get('password') != '') ? 1 : 0; +if($needAuth && !isset($dontStartSession)) +{ + if(Config::get('session') == 'files') + { + session_save_path(MTTPATH. 'tmp/sessions'); + ini_set('session.gc_maxlifetime', '1209600'); # 14 days session file minimum lifetime + ini_set('session.gc_probability', 1); + ini_set('session.gc_divisor', 10); + } + + ini_set('session.use_cookies', true); + ini_set('session.use_only_cookies', true); + session_set_cookie_params(1209600, url_dir(Config::get('url')=='' ? $_SERVER['REQUEST_URI'] : Config::get('url'))); # 14 days session cookie lifetime + session_name('mtt-session'); + session_start(); +} + +function is_logged() +{ + if(!isset($_SESSION['logged']) || !$_SESSION['logged']) return false; + return true; +} + +function is_readonly() +{ + $needAuth = (Config::get('password') != '') ? 1 : 0; + if($needAuth && !is_logged()) return true; + return false; +} + +function timestampToDatetime($timestamp) +{ + $format = Config::get('dateformat') .' '. (Config::get('clock') == 12 ? 'g:i A' : 'H:i'); + return formatTime($format, $timestamp); +} + +function formatTime($format, $timestamp=0) +{ + $lang = Lang::instance(); + if($timestamp == 0) $timestamp = time(); + $newformat = strtr($format, array('F'=>'%1', 'M'=>'%2')); + $adate = explode(',', date('n,'.$newformat, $timestamp), 2); + $s = $adate[1]; + if($newformat != $format) + { + $am = (int)$adate[0]; + $ml = $lang->get('months_long'); + $ms = $lang->get('months_short'); + $F = $ml[$am-1]; + $M = $ms[$am-1]; + $s = strtr($s, array('%1'=>$F, '%2'=>$M)); + } + return $s; +} + +function _e($s) +{ + echo Lang::instance()->get($s); +} + +function __($s) +{ + return Lang::instance()->get($s); +} + +function mttinfo($v) +{ + global $_mttinfo; + if(!isset($_mttinfo[$v])) { + echo get_mttinfo($v); + } else { + echo $_mttinfo[$v]; + } +} + +function get_mttinfo($v) +{ + global $_mttinfo; + if(isset($_mttinfo[$v])) return $_mttinfo[$v]; + switch($v) + { + case 'template_url': + $_mttinfo['template_url'] = get_mttinfo('mtt_url'). 'themes/'. Config::get('template') . '/'; + return $_mttinfo['template_url']; + case 'url': + $_mttinfo['url'] = Config::get('url'); + if($_mttinfo['url'] == '') + $_mttinfo['url'] = 'http://'.$_SERVER['HTTP_HOST'] .($_SERVER['SERVER_PORT'] != 80 ? ':'.$_SERVER['SERVER_PORT'] : ''). + url_dir(isset($_SERVER['REQUEST_URI']) ? $_SERVER['REQUEST_URI'] : $_SERVER['SCRIPT_NAME']); + return $_mttinfo['url']; + case 'mtt_url': + $_mttinfo['mtt_url'] = Config::get('mtt_url'); + if($_mttinfo['mtt_url'] == '') $_mttinfo['mtt_url'] = url_dir(isset($_SERVER['REQUEST_URI']) ? $_SERVER['REQUEST_URI'] : $_SERVER['SCRIPT_NAME']); + return $_mttinfo['mtt_url']; + case 'title': + $_mttinfo['title'] = (Config::get('title') != '') ? htmlarray(Config::get('title')) : __('My Tiny Todolist'); + return $_mttinfo['title']; + } +} + +function jsonExit($data) +{ + header('Content-type: application/json; charset=utf-8'); + echo json_encode($data); + exit; +} + +?> \ No newline at end of file diff --git a/sources/www/jquery/index.html b/sources/www/jquery/index.html new file mode 100644 index 0000000..d1dd79d --- /dev/null +++ b/sources/www/jquery/index.html @@ -0,0 +1 @@ +Place for jQuery UI \ No newline at end of file diff --git a/sources/www/jquery/jquery-1.4.4.min.js b/sources/www/jquery/jquery-1.4.4.min.js new file mode 100644 index 0000000..8f3ca2e --- /dev/null +++ b/sources/www/jquery/jquery-1.4.4.min.js @@ -0,0 +1,167 @@ +/*! + * jQuery JavaScript Library v1.4.4 + * http://jquery.com/ + * + * Copyright 2010, John Resig + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * Includes Sizzle.js + * http://sizzlejs.com/ + * Copyright 2010, The Dojo Foundation + * Released under the MIT, BSD, and GPL Licenses. + * + * Date: Thu Nov 11 19:04:53 2010 -0500 + */ +(function(E,B){function ka(a,b,d){if(d===B&&a.nodeType===1){d=a.getAttribute("data-"+b);if(typeof d==="string"){try{d=d==="true"?true:d==="false"?false:d==="null"?null:!c.isNaN(d)?parseFloat(d):Ja.test(d)?c.parseJSON(d):d}catch(e){}c.data(a,b,d)}else d=B}return d}function U(){return false}function ca(){return true}function la(a,b,d){d[0].type=a;return c.event.handle.apply(b,d)}function Ka(a){var b,d,e,f,h,l,k,o,x,r,A,C=[];f=[];h=c.data(this,this.nodeType?"events":"__events__");if(typeof h==="function")h= +h.events;if(!(a.liveFired===this||!h||!h.live||a.button&&a.type==="click")){if(a.namespace)A=RegExp("(^|\\.)"+a.namespace.split(".").join("\\.(?:.*\\.)?")+"(\\.|$)");a.liveFired=this;var J=h.live.slice(0);for(k=0;kd)break;a.currentTarget=f.elem;a.data=f.handleObj.data;a.handleObj=f.handleObj;A=f.handleObj.origHandler.apply(f.elem,arguments);if(A===false||a.isPropagationStopped()){d=f.level;if(A===false)b=false;if(a.isImmediatePropagationStopped())break}}return b}}function Y(a,b){return(a&&a!=="*"?a+".":"")+b.replace(La, +"`").replace(Ma,"&")}function ma(a,b,d){if(c.isFunction(b))return c.grep(a,function(f,h){return!!b.call(f,h,f)===d});else if(b.nodeType)return c.grep(a,function(f){return f===b===d});else if(typeof b==="string"){var e=c.grep(a,function(f){return f.nodeType===1});if(Na.test(b))return c.filter(b,e,!d);else b=c.filter(b,e)}return c.grep(a,function(f){return c.inArray(f,b)>=0===d})}function na(a,b){var d=0;b.each(function(){if(this.nodeName===(a[d]&&a[d].nodeName)){var e=c.data(a[d++]),f=c.data(this, +e);if(e=e&&e.events){delete f.handle;f.events={};for(var h in e)for(var l in e[h])c.event.add(this,h,e[h][l],e[h][l].data)}}})}function Oa(a,b){b.src?c.ajax({url:b.src,async:false,dataType:"script"}):c.globalEval(b.text||b.textContent||b.innerHTML||"");b.parentNode&&b.parentNode.removeChild(b)}function oa(a,b,d){var e=b==="width"?a.offsetWidth:a.offsetHeight;if(d==="border")return e;c.each(b==="width"?Pa:Qa,function(){d||(e-=parseFloat(c.css(a,"padding"+this))||0);if(d==="margin")e+=parseFloat(c.css(a, +"margin"+this))||0;else e-=parseFloat(c.css(a,"border"+this+"Width"))||0});return e}function da(a,b,d,e){if(c.isArray(b)&&b.length)c.each(b,function(f,h){d||Ra.test(a)?e(a,h):da(a+"["+(typeof h==="object"||c.isArray(h)?f:"")+"]",h,d,e)});else if(!d&&b!=null&&typeof b==="object")c.isEmptyObject(b)?e(a,""):c.each(b,function(f,h){da(a+"["+f+"]",h,d,e)});else e(a,b)}function S(a,b){var d={};c.each(pa.concat.apply([],pa.slice(0,b)),function(){d[this]=a});return d}function qa(a){if(!ea[a]){var b=c("<"+ +a+">").appendTo("body"),d=b.css("display");b.remove();if(d==="none"||d==="")d="block";ea[a]=d}return ea[a]}function fa(a){return c.isWindow(a)?a:a.nodeType===9?a.defaultView||a.parentWindow:false}var t=E.document,c=function(){function a(){if(!b.isReady){try{t.documentElement.doScroll("left")}catch(j){setTimeout(a,1);return}b.ready()}}var b=function(j,s){return new b.fn.init(j,s)},d=E.jQuery,e=E.$,f,h=/^(?:[^<]*(<[\w\W]+>)[^>]*$|#([\w\-]+)$)/,l=/\S/,k=/^\s+/,o=/\s+$/,x=/\W/,r=/\d/,A=/^<(\w+)\s*\/?>(?:<\/\1>)?$/, +C=/^[\],:{}\s]*$/,J=/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g,w=/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g,I=/(?:^|:|,)(?:\s*\[)+/g,L=/(webkit)[ \/]([\w.]+)/,g=/(opera)(?:.*version)?[ \/]([\w.]+)/,i=/(msie) ([\w.]+)/,n=/(mozilla)(?:.*? rv:([\w.]+))?/,m=navigator.userAgent,p=false,q=[],u,y=Object.prototype.toString,F=Object.prototype.hasOwnProperty,M=Array.prototype.push,N=Array.prototype.slice,O=String.prototype.trim,D=Array.prototype.indexOf,R={};b.fn=b.prototype={init:function(j, +s){var v,z,H;if(!j)return this;if(j.nodeType){this.context=this[0]=j;this.length=1;return this}if(j==="body"&&!s&&t.body){this.context=t;this[0]=t.body;this.selector="body";this.length=1;return this}if(typeof j==="string")if((v=h.exec(j))&&(v[1]||!s))if(v[1]){H=s?s.ownerDocument||s:t;if(z=A.exec(j))if(b.isPlainObject(s)){j=[t.createElement(z[1])];b.fn.attr.call(j,s,true)}else j=[H.createElement(z[1])];else{z=b.buildFragment([v[1]],[H]);j=(z.cacheable?z.fragment.cloneNode(true):z.fragment).childNodes}return b.merge(this, +j)}else{if((z=t.getElementById(v[2]))&&z.parentNode){if(z.id!==v[2])return f.find(j);this.length=1;this[0]=z}this.context=t;this.selector=j;return this}else if(!s&&!x.test(j)){this.selector=j;this.context=t;j=t.getElementsByTagName(j);return b.merge(this,j)}else return!s||s.jquery?(s||f).find(j):b(s).find(j);else if(b.isFunction(j))return f.ready(j);if(j.selector!==B){this.selector=j.selector;this.context=j.context}return b.makeArray(j,this)},selector:"",jquery:"1.4.4",length:0,size:function(){return this.length}, +toArray:function(){return N.call(this,0)},get:function(j){return j==null?this.toArray():j<0?this.slice(j)[0]:this[j]},pushStack:function(j,s,v){var z=b();b.isArray(j)?M.apply(z,j):b.merge(z,j);z.prevObject=this;z.context=this.context;if(s==="find")z.selector=this.selector+(this.selector?" ":"")+v;else if(s)z.selector=this.selector+"."+s+"("+v+")";return z},each:function(j,s){return b.each(this,j,s)},ready:function(j){b.bindReady();if(b.isReady)j.call(t,b);else q&&q.push(j);return this},eq:function(j){return j=== +-1?this.slice(j):this.slice(j,+j+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(N.apply(this,arguments),"slice",N.call(arguments).join(","))},map:function(j){return this.pushStack(b.map(this,function(s,v){return j.call(s,v,s)}))},end:function(){return this.prevObject||b(null)},push:M,sort:[].sort,splice:[].splice};b.fn.init.prototype=b.fn;b.extend=b.fn.extend=function(){var j,s,v,z,H,G=arguments[0]||{},K=1,Q=arguments.length,ga=false; +if(typeof G==="boolean"){ga=G;G=arguments[1]||{};K=2}if(typeof G!=="object"&&!b.isFunction(G))G={};if(Q===K){G=this;--K}for(;K0))if(q){var s=0,v=q;for(q=null;j=v[s++];)j.call(t,b);b.fn.trigger&&b(t).trigger("ready").unbind("ready")}}},bindReady:function(){if(!p){p=true;if(t.readyState==="complete")return setTimeout(b.ready,1);if(t.addEventListener){t.addEventListener("DOMContentLoaded",u,false);E.addEventListener("load",b.ready,false)}else if(t.attachEvent){t.attachEvent("onreadystatechange",u);E.attachEvent("onload", +b.ready);var j=false;try{j=E.frameElement==null}catch(s){}t.documentElement.doScroll&&j&&a()}}},isFunction:function(j){return b.type(j)==="function"},isArray:Array.isArray||function(j){return b.type(j)==="array"},isWindow:function(j){return j&&typeof j==="object"&&"setInterval"in j},isNaN:function(j){return j==null||!r.test(j)||isNaN(j)},type:function(j){return j==null?String(j):R[y.call(j)]||"object"},isPlainObject:function(j){if(!j||b.type(j)!=="object"||j.nodeType||b.isWindow(j))return false;if(j.constructor&& +!F.call(j,"constructor")&&!F.call(j.constructor.prototype,"isPrototypeOf"))return false;for(var s in j);return s===B||F.call(j,s)},isEmptyObject:function(j){for(var s in j)return false;return true},error:function(j){throw j;},parseJSON:function(j){if(typeof j!=="string"||!j)return null;j=b.trim(j);if(C.test(j.replace(J,"@").replace(w,"]").replace(I,"")))return E.JSON&&E.JSON.parse?E.JSON.parse(j):(new Function("return "+j))();else b.error("Invalid JSON: "+j)},noop:function(){},globalEval:function(j){if(j&& +l.test(j)){var s=t.getElementsByTagName("head")[0]||t.documentElement,v=t.createElement("script");v.type="text/javascript";if(b.support.scriptEval)v.appendChild(t.createTextNode(j));else v.text=j;s.insertBefore(v,s.firstChild);s.removeChild(v)}},nodeName:function(j,s){return j.nodeName&&j.nodeName.toUpperCase()===s.toUpperCase()},each:function(j,s,v){var z,H=0,G=j.length,K=G===B||b.isFunction(j);if(v)if(K)for(z in j){if(s.apply(j[z],v)===false)break}else for(;H
a";var f=d.getElementsByTagName("*"),h=d.getElementsByTagName("a")[0],l=t.createElement("select"), +k=l.appendChild(t.createElement("option"));if(!(!f||!f.length||!h)){c.support={leadingWhitespace:d.firstChild.nodeType===3,tbody:!d.getElementsByTagName("tbody").length,htmlSerialize:!!d.getElementsByTagName("link").length,style:/red/.test(h.getAttribute("style")),hrefNormalized:h.getAttribute("href")==="/a",opacity:/^0.55$/.test(h.style.opacity),cssFloat:!!h.style.cssFloat,checkOn:d.getElementsByTagName("input")[0].value==="on",optSelected:k.selected,deleteExpando:true,optDisabled:false,checkClone:false, +scriptEval:false,noCloneEvent:true,boxModel:null,inlineBlockNeedsLayout:false,shrinkWrapBlocks:false,reliableHiddenOffsets:true};l.disabled=true;c.support.optDisabled=!k.disabled;b.type="text/javascript";try{b.appendChild(t.createTextNode("window."+e+"=1;"))}catch(o){}a.insertBefore(b,a.firstChild);if(E[e]){c.support.scriptEval=true;delete E[e]}try{delete b.test}catch(x){c.support.deleteExpando=false}a.removeChild(b);if(d.attachEvent&&d.fireEvent){d.attachEvent("onclick",function r(){c.support.noCloneEvent= +false;d.detachEvent("onclick",r)});d.cloneNode(true).fireEvent("onclick")}d=t.createElement("div");d.innerHTML="";a=t.createDocumentFragment();a.appendChild(d.firstChild);c.support.checkClone=a.cloneNode(true).cloneNode(true).lastChild.checked;c(function(){var r=t.createElement("div");r.style.width=r.style.paddingLeft="1px";t.body.appendChild(r);c.boxModel=c.support.boxModel=r.offsetWidth===2;if("zoom"in r.style){r.style.display="inline";r.style.zoom= +1;c.support.inlineBlockNeedsLayout=r.offsetWidth===2;r.style.display="";r.innerHTML="
";c.support.shrinkWrapBlocks=r.offsetWidth!==2}r.innerHTML="
t
";var A=r.getElementsByTagName("td");c.support.reliableHiddenOffsets=A[0].offsetHeight===0;A[0].style.display="";A[1].style.display="none";c.support.reliableHiddenOffsets=c.support.reliableHiddenOffsets&&A[0].offsetHeight===0;r.innerHTML="";t.body.removeChild(r).style.display= +"none"});a=function(r){var A=t.createElement("div");r="on"+r;var C=r in A;if(!C){A.setAttribute(r,"return;");C=typeof A[r]==="function"}return C};c.support.submitBubbles=a("submit");c.support.changeBubbles=a("change");a=b=d=f=h=null}})();var ra={},Ja=/^(?:\{.*\}|\[.*\])$/;c.extend({cache:{},uuid:0,expando:"jQuery"+c.now(),noData:{embed:true,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:true},data:function(a,b,d){if(c.acceptData(a)){a=a==E?ra:a;var e=a.nodeType,f=e?a[c.expando]:null,h= +c.cache;if(!(e&&!f&&typeof b==="string"&&d===B)){if(e)f||(a[c.expando]=f=++c.uuid);else h=a;if(typeof b==="object")if(e)h[f]=c.extend(h[f],b);else c.extend(h,b);else if(e&&!h[f])h[f]={};a=e?h[f]:h;if(d!==B)a[b]=d;return typeof b==="string"?a[b]:a}}},removeData:function(a,b){if(c.acceptData(a)){a=a==E?ra:a;var d=a.nodeType,e=d?a[c.expando]:a,f=c.cache,h=d?f[e]:e;if(b){if(h){delete h[b];d&&c.isEmptyObject(h)&&c.removeData(a)}}else if(d&&c.support.deleteExpando)delete a[c.expando];else if(a.removeAttribute)a.removeAttribute(c.expando); +else if(d)delete f[e];else for(var l in a)delete a[l]}},acceptData:function(a){if(a.nodeName){var b=c.noData[a.nodeName.toLowerCase()];if(b)return!(b===true||a.getAttribute("classid")!==b)}return true}});c.fn.extend({data:function(a,b){var d=null;if(typeof a==="undefined"){if(this.length){var e=this[0].attributes,f;d=c.data(this[0]);for(var h=0,l=e.length;h-1)return true;return false},val:function(a){if(!arguments.length){var b=this[0];if(b){if(c.nodeName(b,"option")){var d=b.attributes.value;return!d||d.specified?b.value:b.text}if(c.nodeName(b,"select")){var e=b.selectedIndex;d=[];var f=b.options;b=b.type==="select-one"; +if(e<0)return null;var h=b?e:0;for(e=b?e+1:f.length;h=0;else if(c.nodeName(this,"select")){var A=c.makeArray(r);c("option",this).each(function(){this.selected=c.inArray(c(this).val(),A)>=0});if(!A.length)this.selectedIndex=-1}else this.value=r}})}});c.extend({attrFn:{val:true,css:true,html:true,text:true,data:true,width:true,height:true,offset:true}, +attr:function(a,b,d,e){if(!a||a.nodeType===3||a.nodeType===8)return B;if(e&&b in c.attrFn)return c(a)[b](d);e=a.nodeType!==1||!c.isXMLDoc(a);var f=d!==B;b=e&&c.props[b]||b;var h=Ta.test(b);if((b in a||a[b]!==B)&&e&&!h){if(f){b==="type"&&Ua.test(a.nodeName)&&a.parentNode&&c.error("type property can't be changed");if(d===null)a.nodeType===1&&a.removeAttribute(b);else a[b]=d}if(c.nodeName(a,"form")&&a.getAttributeNode(b))return a.getAttributeNode(b).nodeValue;if(b==="tabIndex")return(b=a.getAttributeNode("tabIndex"))&& +b.specified?b.value:Va.test(a.nodeName)||Wa.test(a.nodeName)&&a.href?0:B;return a[b]}if(!c.support.style&&e&&b==="style"){if(f)a.style.cssText=""+d;return a.style.cssText}f&&a.setAttribute(b,""+d);if(!a.attributes[b]&&a.hasAttribute&&!a.hasAttribute(b))return B;a=!c.support.hrefNormalized&&e&&h?a.getAttribute(b,2):a.getAttribute(b);return a===null?B:a}});var X=/\.(.*)$/,ia=/^(?:textarea|input|select)$/i,La=/\./g,Ma=/ /g,Xa=/[^\w\s.|`]/g,Ya=function(a){return a.replace(Xa,"\\$&")},ua={focusin:0,focusout:0}; +c.event={add:function(a,b,d,e){if(!(a.nodeType===3||a.nodeType===8)){if(c.isWindow(a)&&a!==E&&!a.frameElement)a=E;if(d===false)d=U;else if(!d)return;var f,h;if(d.handler){f=d;d=f.handler}if(!d.guid)d.guid=c.guid++;if(h=c.data(a)){var l=a.nodeType?"events":"__events__",k=h[l],o=h.handle;if(typeof k==="function"){o=k.handle;k=k.events}else if(!k){a.nodeType||(h[l]=h=function(){});h.events=k={}}if(!o)h.handle=o=function(){return typeof c!=="undefined"&&!c.event.triggered?c.event.handle.apply(o.elem, +arguments):B};o.elem=a;b=b.split(" ");for(var x=0,r;l=b[x++];){h=f?c.extend({},f):{handler:d,data:e};if(l.indexOf(".")>-1){r=l.split(".");l=r.shift();h.namespace=r.slice(0).sort().join(".")}else{r=[];h.namespace=""}h.type=l;if(!h.guid)h.guid=d.guid;var A=k[l],C=c.event.special[l]||{};if(!A){A=k[l]=[];if(!C.setup||C.setup.call(a,e,r,o)===false)if(a.addEventListener)a.addEventListener(l,o,false);else a.attachEvent&&a.attachEvent("on"+l,o)}if(C.add){C.add.call(a,h);if(!h.handler.guid)h.handler.guid= +d.guid}A.push(h);c.event.global[l]=true}a=null}}},global:{},remove:function(a,b,d,e){if(!(a.nodeType===3||a.nodeType===8)){if(d===false)d=U;var f,h,l=0,k,o,x,r,A,C,J=a.nodeType?"events":"__events__",w=c.data(a),I=w&&w[J];if(w&&I){if(typeof I==="function"){w=I;I=I.events}if(b&&b.type){d=b.handler;b=b.type}if(!b||typeof b==="string"&&b.charAt(0)==="."){b=b||"";for(f in I)c.event.remove(a,f+b)}else{for(b=b.split(" ");f=b[l++];){r=f;k=f.indexOf(".")<0;o=[];if(!k){o=f.split(".");f=o.shift();x=RegExp("(^|\\.)"+ +c.map(o.slice(0).sort(),Ya).join("\\.(?:.*\\.)?")+"(\\.|$)")}if(A=I[f])if(d){r=c.event.special[f]||{};for(h=e||0;h=0){a.type=f=f.slice(0,-1);a.exclusive=true}if(!d){a.stopPropagation();c.event.global[f]&&c.each(c.cache,function(){this.events&&this.events[f]&&c.event.trigger(a,b,this.handle.elem)})}if(!d||d.nodeType===3||d.nodeType=== +8)return B;a.result=B;a.target=d;b=c.makeArray(b);b.unshift(a)}a.currentTarget=d;(e=d.nodeType?c.data(d,"handle"):(c.data(d,"__events__")||{}).handle)&&e.apply(d,b);e=d.parentNode||d.ownerDocument;try{if(!(d&&d.nodeName&&c.noData[d.nodeName.toLowerCase()]))if(d["on"+f]&&d["on"+f].apply(d,b)===false){a.result=false;a.preventDefault()}}catch(h){}if(!a.isPropagationStopped()&&e)c.event.trigger(a,b,e,true);else if(!a.isDefaultPrevented()){var l;e=a.target;var k=f.replace(X,""),o=c.nodeName(e,"a")&&k=== +"click",x=c.event.special[k]||{};if((!x._default||x._default.call(d,a)===false)&&!o&&!(e&&e.nodeName&&c.noData[e.nodeName.toLowerCase()])){try{if(e[k]){if(l=e["on"+k])e["on"+k]=null;c.event.triggered=true;e[k]()}}catch(r){}if(l)e["on"+k]=l;c.event.triggered=false}}},handle:function(a){var b,d,e,f;d=[];var h=c.makeArray(arguments);a=h[0]=c.event.fix(a||E.event);a.currentTarget=this;b=a.type.indexOf(".")<0&&!a.exclusive;if(!b){e=a.type.split(".");a.type=e.shift();d=e.slice(0).sort();e=RegExp("(^|\\.)"+ +d.join("\\.(?:.*\\.)?")+"(\\.|$)")}a.namespace=a.namespace||d.join(".");f=c.data(this,this.nodeType?"events":"__events__");if(typeof f==="function")f=f.events;d=(f||{})[a.type];if(f&&d){d=d.slice(0);f=0;for(var l=d.length;f-1?c.map(a.options,function(e){return e.selected}).join("-"):"";else if(a.nodeName.toLowerCase()==="select")d=a.selectedIndex;return d},Z=function(a,b){var d=a.target,e,f;if(!(!ia.test(d.nodeName)||d.readOnly)){e=c.data(d,"_change_data");f=xa(d);if(a.type!=="focusout"||d.type!=="radio")c.data(d,"_change_data",f);if(!(e===B||f===e))if(e!=null||f){a.type="change";a.liveFired= +B;return c.event.trigger(a,b,d)}}};c.event.special.change={filters:{focusout:Z,beforedeactivate:Z,click:function(a){var b=a.target,d=b.type;if(d==="radio"||d==="checkbox"||b.nodeName.toLowerCase()==="select")return Z.call(this,a)},keydown:function(a){var b=a.target,d=b.type;if(a.keyCode===13&&b.nodeName.toLowerCase()!=="textarea"||a.keyCode===32&&(d==="checkbox"||d==="radio")||d==="select-multiple")return Z.call(this,a)},beforeactivate:function(a){a=a.target;c.data(a,"_change_data",xa(a))}},setup:function(){if(this.type=== +"file")return false;for(var a in V)c.event.add(this,a+".specialChange",V[a]);return ia.test(this.nodeName)},teardown:function(){c.event.remove(this,".specialChange");return ia.test(this.nodeName)}};V=c.event.special.change.filters;V.focus=V.beforeactivate}t.addEventListener&&c.each({focus:"focusin",blur:"focusout"},function(a,b){function d(e){e=c.event.fix(e);e.type=b;return c.event.trigger(e,null,e.target)}c.event.special[b]={setup:function(){ua[b]++===0&&t.addEventListener(a,d,true)},teardown:function(){--ua[b]=== +0&&t.removeEventListener(a,d,true)}}});c.each(["bind","one"],function(a,b){c.fn[b]=function(d,e,f){if(typeof d==="object"){for(var h in d)this[b](h,e,d[h],f);return this}if(c.isFunction(e)||e===false){f=e;e=B}var l=b==="one"?c.proxy(f,function(o){c(this).unbind(o,l);return f.apply(this,arguments)}):f;if(d==="unload"&&b!=="one")this.one(d,e,f);else{h=0;for(var k=this.length;h0?this.bind(b,d,e):this.trigger(b)};if(c.attrFn)c.attrFn[b]=true});E.attachEvent&&!E.addEventListener&&c(E).bind("unload",function(){for(var a in c.cache)if(c.cache[a].handle)try{c.event.remove(c.cache[a].handle.elem)}catch(b){}}); +(function(){function a(g,i,n,m,p,q){p=0;for(var u=m.length;p0){F=y;break}}y=y[g]}m[p]=F}}}var d=/((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,e=0,f=Object.prototype.toString,h=false,l=true;[0,0].sort(function(){l=false;return 0});var k=function(g,i,n,m){n=n||[];var p=i=i||t;if(i.nodeType!==1&&i.nodeType!==9)return[];if(!g||typeof g!=="string")return n;var q,u,y,F,M,N=true,O=k.isXML(i),D=[],R=g;do{d.exec("");if(q=d.exec(R)){R=q[3];D.push(q[1]);if(q[2]){F=q[3]; +break}}}while(q);if(D.length>1&&x.exec(g))if(D.length===2&&o.relative[D[0]])u=L(D[0]+D[1],i);else for(u=o.relative[D[0]]?[i]:k(D.shift(),i);D.length;){g=D.shift();if(o.relative[g])g+=D.shift();u=L(g,u)}else{if(!m&&D.length>1&&i.nodeType===9&&!O&&o.match.ID.test(D[0])&&!o.match.ID.test(D[D.length-1])){q=k.find(D.shift(),i,O);i=q.expr?k.filter(q.expr,q.set)[0]:q.set[0]}if(i){q=m?{expr:D.pop(),set:C(m)}:k.find(D.pop(),D.length===1&&(D[0]==="~"||D[0]==="+")&&i.parentNode?i.parentNode:i,O);u=q.expr?k.filter(q.expr, +q.set):q.set;if(D.length>0)y=C(u);else N=false;for(;D.length;){q=M=D.pop();if(o.relative[M])q=D.pop();else M="";if(q==null)q=i;o.relative[M](y,q,O)}}else y=[]}y||(y=u);y||k.error(M||g);if(f.call(y)==="[object Array]")if(N)if(i&&i.nodeType===1)for(g=0;y[g]!=null;g++){if(y[g]&&(y[g]===true||y[g].nodeType===1&&k.contains(i,y[g])))n.push(u[g])}else for(g=0;y[g]!=null;g++)y[g]&&y[g].nodeType===1&&n.push(u[g]);else n.push.apply(n,y);else C(y,n);if(F){k(F,p,n,m);k.uniqueSort(n)}return n};k.uniqueSort=function(g){if(w){h= +l;g.sort(w);if(h)for(var i=1;i0};k.find=function(g,i,n){var m;if(!g)return[];for(var p=0,q=o.order.length;p":function(g,i){var n,m=typeof i==="string",p=0,q=g.length;if(m&&!/\W/.test(i))for(i=i.toLowerCase();p=0))n||m.push(u);else if(n)i[q]=false;return false},ID:function(g){return g[1].replace(/\\/g,"")},TAG:function(g){return g[1].toLowerCase()},CHILD:function(g){if(g[1]==="nth"){var i=/(-?)(\d*)n((?:\+|-)?\d*)/.exec(g[2]==="even"&&"2n"||g[2]==="odd"&&"2n+1"||!/\D/.test(g[2])&&"0n+"+g[2]||g[2]);g[2]=i[1]+(i[2]||1)-0;g[3]=i[3]-0}g[0]=e++;return g},ATTR:function(g,i,n, +m,p,q){i=g[1].replace(/\\/g,"");if(!q&&o.attrMap[i])g[1]=o.attrMap[i];if(g[2]==="~=")g[4]=" "+g[4]+" ";return g},PSEUDO:function(g,i,n,m,p){if(g[1]==="not")if((d.exec(g[3])||"").length>1||/^\w/.test(g[3]))g[3]=k(g[3],null,null,i);else{g=k.filter(g[3],i,n,true^p);n||m.push.apply(m,g);return false}else if(o.match.POS.test(g[0])||o.match.CHILD.test(g[0]))return true;return g},POS:function(g){g.unshift(true);return g}},filters:{enabled:function(g){return g.disabled===false&&g.type!=="hidden"},disabled:function(g){return g.disabled=== +true},checked:function(g){return g.checked===true},selected:function(g){return g.selected===true},parent:function(g){return!!g.firstChild},empty:function(g){return!g.firstChild},has:function(g,i,n){return!!k(n[3],g).length},header:function(g){return/h\d/i.test(g.nodeName)},text:function(g){return"text"===g.type},radio:function(g){return"radio"===g.type},checkbox:function(g){return"checkbox"===g.type},file:function(g){return"file"===g.type},password:function(g){return"password"===g.type},submit:function(g){return"submit"=== +g.type},image:function(g){return"image"===g.type},reset:function(g){return"reset"===g.type},button:function(g){return"button"===g.type||g.nodeName.toLowerCase()==="button"},input:function(g){return/input|select|textarea|button/i.test(g.nodeName)}},setFilters:{first:function(g,i){return i===0},last:function(g,i,n,m){return i===m.length-1},even:function(g,i){return i%2===0},odd:function(g,i){return i%2===1},lt:function(g,i,n){return in[3]-0},nth:function(g,i,n){return n[3]- +0===i},eq:function(g,i,n){return n[3]-0===i}},filter:{PSEUDO:function(g,i,n,m){var p=i[1],q=o.filters[p];if(q)return q(g,n,i,m);else if(p==="contains")return(g.textContent||g.innerText||k.getText([g])||"").indexOf(i[3])>=0;else if(p==="not"){i=i[3];n=0;for(m=i.length;n=0}},ID:function(g,i){return g.nodeType===1&&g.getAttribute("id")===i},TAG:function(g,i){return i==="*"&&g.nodeType===1||g.nodeName.toLowerCase()=== +i},CLASS:function(g,i){return(" "+(g.className||g.getAttribute("class"))+" ").indexOf(i)>-1},ATTR:function(g,i){var n=i[1];n=o.attrHandle[n]?o.attrHandle[n](g):g[n]!=null?g[n]:g.getAttribute(n);var m=n+"",p=i[2],q=i[4];return n==null?p==="!=":p==="="?m===q:p==="*="?m.indexOf(q)>=0:p==="~="?(" "+m+" ").indexOf(q)>=0:!q?m&&n!==false:p==="!="?m!==q:p==="^="?m.indexOf(q)===0:p==="$="?m.substr(m.length-q.length)===q:p==="|="?m===q||m.substr(0,q.length+1)===q+"-":false},POS:function(g,i,n,m){var p=o.setFilters[i[2]]; +if(p)return p(g,n,i,m)}}},x=o.match.POS,r=function(g,i){return"\\"+(i-0+1)},A;for(A in o.match){o.match[A]=RegExp(o.match[A].source+/(?![^\[]*\])(?![^\(]*\))/.source);o.leftMatch[A]=RegExp(/(^(?:.|\r|\n)*?)/.source+o.match[A].source.replace(/\\(\d+)/g,r))}var C=function(g,i){g=Array.prototype.slice.call(g,0);if(i){i.push.apply(i,g);return i}return g};try{Array.prototype.slice.call(t.documentElement.childNodes,0)}catch(J){C=function(g,i){var n=0,m=i||[];if(f.call(g)==="[object Array]")Array.prototype.push.apply(m, +g);else if(typeof g.length==="number")for(var p=g.length;n";n.insertBefore(g,n.firstChild);if(t.getElementById(i)){o.find.ID=function(m,p,q){if(typeof p.getElementById!=="undefined"&&!q)return(p=p.getElementById(m[1]))?p.id===m[1]||typeof p.getAttributeNode!=="undefined"&&p.getAttributeNode("id").nodeValue===m[1]?[p]:B:[]};o.filter.ID=function(m,p){var q=typeof m.getAttributeNode!=="undefined"&&m.getAttributeNode("id");return m.nodeType===1&&q&&q.nodeValue===p}}n.removeChild(g); +n=g=null})();(function(){var g=t.createElement("div");g.appendChild(t.createComment(""));if(g.getElementsByTagName("*").length>0)o.find.TAG=function(i,n){var m=n.getElementsByTagName(i[1]);if(i[1]==="*"){for(var p=[],q=0;m[q];q++)m[q].nodeType===1&&p.push(m[q]);m=p}return m};g.innerHTML="";if(g.firstChild&&typeof g.firstChild.getAttribute!=="undefined"&&g.firstChild.getAttribute("href")!=="#")o.attrHandle.href=function(i){return i.getAttribute("href",2)};g=null})();t.querySelectorAll&& +function(){var g=k,i=t.createElement("div");i.innerHTML="

";if(!(i.querySelectorAll&&i.querySelectorAll(".TEST").length===0)){k=function(m,p,q,u){p=p||t;m=m.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!u&&!k.isXML(p))if(p.nodeType===9)try{return C(p.querySelectorAll(m),q)}catch(y){}else if(p.nodeType===1&&p.nodeName.toLowerCase()!=="object"){var F=p.getAttribute("id"),M=F||"__sizzle__";F||p.setAttribute("id",M);try{return C(p.querySelectorAll("#"+M+" "+m),q)}catch(N){}finally{F|| +p.removeAttribute("id")}}return g(m,p,q,u)};for(var n in g)k[n]=g[n];i=null}}();(function(){var g=t.documentElement,i=g.matchesSelector||g.mozMatchesSelector||g.webkitMatchesSelector||g.msMatchesSelector,n=false;try{i.call(t.documentElement,"[test!='']:sizzle")}catch(m){n=true}if(i)k.matchesSelector=function(p,q){q=q.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!k.isXML(p))try{if(n||!o.match.PSEUDO.test(q)&&!/!=/.test(q))return i.call(p,q)}catch(u){}return k(q,null,null,[p]).length>0}})();(function(){var g= +t.createElement("div");g.innerHTML="
";if(!(!g.getElementsByClassName||g.getElementsByClassName("e").length===0)){g.lastChild.className="e";if(g.getElementsByClassName("e").length!==1){o.order.splice(1,0,"CLASS");o.find.CLASS=function(i,n,m){if(typeof n.getElementsByClassName!=="undefined"&&!m)return n.getElementsByClassName(i[1])};g=null}}})();k.contains=t.documentElement.contains?function(g,i){return g!==i&&(g.contains?g.contains(i):true)}:t.documentElement.compareDocumentPosition? +function(g,i){return!!(g.compareDocumentPosition(i)&16)}:function(){return false};k.isXML=function(g){return(g=(g?g.ownerDocument||g:0).documentElement)?g.nodeName!=="HTML":false};var L=function(g,i){for(var n,m=[],p="",q=i.nodeType?[i]:i;n=o.match.PSEUDO.exec(g);){p+=n[0];g=g.replace(o.match.PSEUDO,"")}g=o.relative[g]?g+"*":g;n=0;for(var u=q.length;n0)for(var h=d;h0},closest:function(a,b){var d=[],e,f,h=this[0];if(c.isArray(a)){var l,k={},o=1;if(h&&a.length){e=0;for(f=a.length;e-1:c(h).is(e))d.push({selector:l,elem:h,level:o})}h= +h.parentNode;o++}}return d}l=cb.test(a)?c(a,b||this.context):null;e=0;for(f=this.length;e-1:c.find.matchesSelector(h,a)){d.push(h);break}else{h=h.parentNode;if(!h||!h.ownerDocument||h===b)break}d=d.length>1?c.unique(d):d;return this.pushStack(d,"closest",a)},index:function(a){if(!a||typeof a==="string")return c.inArray(this[0],a?c(a):this.parent().children());return c.inArray(a.jquery?a[0]:a,this)},add:function(a,b){var d=typeof a==="string"?c(a,b||this.context): +c.makeArray(a),e=c.merge(this.get(),d);return this.pushStack(!d[0]||!d[0].parentNode||d[0].parentNode.nodeType===11||!e[0]||!e[0].parentNode||e[0].parentNode.nodeType===11?e:c.unique(e))},andSelf:function(){return this.add(this.prevObject)}});c.each({parent:function(a){return(a=a.parentNode)&&a.nodeType!==11?a:null},parents:function(a){return c.dir(a,"parentNode")},parentsUntil:function(a,b,d){return c.dir(a,"parentNode",d)},next:function(a){return c.nth(a,2,"nextSibling")},prev:function(a){return c.nth(a, +2,"previousSibling")},nextAll:function(a){return c.dir(a,"nextSibling")},prevAll:function(a){return c.dir(a,"previousSibling")},nextUntil:function(a,b,d){return c.dir(a,"nextSibling",d)},prevUntil:function(a,b,d){return c.dir(a,"previousSibling",d)},siblings:function(a){return c.sibling(a.parentNode.firstChild,a)},children:function(a){return c.sibling(a.firstChild)},contents:function(a){return c.nodeName(a,"iframe")?a.contentDocument||a.contentWindow.document:c.makeArray(a.childNodes)}},function(a, +b){c.fn[a]=function(d,e){var f=c.map(this,b,d);Za.test(a)||(e=d);if(e&&typeof e==="string")f=c.filter(e,f);f=this.length>1?c.unique(f):f;if((this.length>1||ab.test(e))&&$a.test(a))f=f.reverse();return this.pushStack(f,a,bb.call(arguments).join(","))}});c.extend({filter:function(a,b,d){if(d)a=":not("+a+")";return b.length===1?c.find.matchesSelector(b[0],a)?[b[0]]:[]:c.find.matches(a,b)},dir:function(a,b,d){var e=[];for(a=a[b];a&&a.nodeType!==9&&(d===B||a.nodeType!==1||!c(a).is(d));){a.nodeType===1&& +e.push(a);a=a[b]}return e},nth:function(a,b,d){b=b||1;for(var e=0;a;a=a[d])if(a.nodeType===1&&++e===b)break;return a},sibling:function(a,b){for(var d=[];a;a=a.nextSibling)a.nodeType===1&&a!==b&&d.push(a);return d}});var za=/ jQuery\d+="(?:\d+|null)"/g,$=/^\s+/,Aa=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,Ba=/<([\w:]+)/,db=/\s]+\/)>/g,P={option:[1, +""],legend:[1,"
","
"],thead:[1,"","
"],tr:[2,"","
"],td:[3,"","
"],col:[2,"","
"],area:[1,"",""],_default:[0,"",""]};P.optgroup=P.option;P.tbody=P.tfoot=P.colgroup=P.caption=P.thead;P.th=P.td;if(!c.support.htmlSerialize)P._default=[1,"div
","
"];c.fn.extend({text:function(a){if(c.isFunction(a))return this.each(function(b){var d= +c(this);d.text(a.call(this,b,d.text()))});if(typeof a!=="object"&&a!==B)return this.empty().append((this[0]&&this[0].ownerDocument||t).createTextNode(a));return c.text(this)},wrapAll:function(a){if(c.isFunction(a))return this.each(function(d){c(this).wrapAll(a.call(this,d))});if(this[0]){var b=c(a,this[0].ownerDocument).eq(0).clone(true);this[0].parentNode&&b.insertBefore(this[0]);b.map(function(){for(var d=this;d.firstChild&&d.firstChild.nodeType===1;)d=d.firstChild;return d}).append(this)}return this}, +wrapInner:function(a){if(c.isFunction(a))return this.each(function(b){c(this).wrapInner(a.call(this,b))});return this.each(function(){var b=c(this),d=b.contents();d.length?d.wrapAll(a):b.append(a)})},wrap:function(a){return this.each(function(){c(this).wrapAll(a)})},unwrap:function(){return this.parent().each(function(){c.nodeName(this,"body")||c(this).replaceWith(this.childNodes)}).end()},append:function(){return this.domManip(arguments,true,function(a){this.nodeType===1&&this.appendChild(a)})}, +prepend:function(){return this.domManip(arguments,true,function(a){this.nodeType===1&&this.insertBefore(a,this.firstChild)})},before:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,false,function(b){this.parentNode.insertBefore(b,this)});else if(arguments.length){var a=c(arguments[0]);a.push.apply(a,this.toArray());return this.pushStack(a,"before",arguments)}},after:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,false,function(b){this.parentNode.insertBefore(b, +this.nextSibling)});else if(arguments.length){var a=this.pushStack(this,"after",arguments);a.push.apply(a,c(arguments[0]).toArray());return a}},remove:function(a,b){for(var d=0,e;(e=this[d])!=null;d++)if(!a||c.filter(a,[e]).length){if(!b&&e.nodeType===1){c.cleanData(e.getElementsByTagName("*"));c.cleanData([e])}e.parentNode&&e.parentNode.removeChild(e)}return this},empty:function(){for(var a=0,b;(b=this[a])!=null;a++)for(b.nodeType===1&&c.cleanData(b.getElementsByTagName("*"));b.firstChild;)b.removeChild(b.firstChild); +return this},clone:function(a){var b=this.map(function(){if(!c.support.noCloneEvent&&!c.isXMLDoc(this)){var d=this.outerHTML,e=this.ownerDocument;if(!d){d=e.createElement("div");d.appendChild(this.cloneNode(true));d=d.innerHTML}return c.clean([d.replace(za,"").replace(fb,'="$1">').replace($,"")],e)[0]}else return this.cloneNode(true)});if(a===true){na(this,b);na(this.find("*"),b.find("*"))}return b},html:function(a){if(a===B)return this[0]&&this[0].nodeType===1?this[0].innerHTML.replace(za,""):null; +else if(typeof a==="string"&&!Ca.test(a)&&(c.support.leadingWhitespace||!$.test(a))&&!P[(Ba.exec(a)||["",""])[1].toLowerCase()]){a=a.replace(Aa,"<$1>");try{for(var b=0,d=this.length;b0||e.cacheable||this.length>1?h.cloneNode(true):h)}k.length&&c.each(k,Oa)}return this}});c.buildFragment=function(a,b,d){var e,f,h;b=b&&b[0]?b[0].ownerDocument||b[0]:t;if(a.length===1&&typeof a[0]==="string"&&a[0].length<512&&b===t&&!Ca.test(a[0])&&(c.support.checkClone||!Da.test(a[0]))){f=true;if(h=c.fragments[a[0]])if(h!==1)e=h}if(!e){e=b.createDocumentFragment();c.clean(a,b,e,d)}if(f)c.fragments[a[0]]=h?e:1;return{fragment:e,cacheable:f}};c.fragments={};c.each({appendTo:"append", +prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(a,b){c.fn[a]=function(d){var e=[];d=c(d);var f=this.length===1&&this[0].parentNode;if(f&&f.nodeType===11&&f.childNodes.length===1&&d.length===1){d[b](this[0]);return this}else{f=0;for(var h=d.length;f0?this.clone(true):this).get();c(d[f])[b](l);e=e.concat(l)}return this.pushStack(e,a,d.selector)}}});c.extend({clean:function(a,b,d,e){b=b||t;if(typeof b.createElement==="undefined")b=b.ownerDocument|| +b[0]&&b[0].ownerDocument||t;for(var f=[],h=0,l;(l=a[h])!=null;h++){if(typeof l==="number")l+="";if(l){if(typeof l==="string"&&!eb.test(l))l=b.createTextNode(l);else if(typeof l==="string"){l=l.replace(Aa,"<$1>");var k=(Ba.exec(l)||["",""])[1].toLowerCase(),o=P[k]||P._default,x=o[0],r=b.createElement("div");for(r.innerHTML=o[1]+l+o[2];x--;)r=r.lastChild;if(!c.support.tbody){x=db.test(l);k=k==="table"&&!x?r.firstChild&&r.firstChild.childNodes:o[1]===""&&!x?r.childNodes:[];for(o=k.length- +1;o>=0;--o)c.nodeName(k[o],"tbody")&&!k[o].childNodes.length&&k[o].parentNode.removeChild(k[o])}!c.support.leadingWhitespace&&$.test(l)&&r.insertBefore(b.createTextNode($.exec(l)[0]),r.firstChild);l=r.childNodes}if(l.nodeType)f.push(l);else f=c.merge(f,l)}}if(d)for(h=0;f[h];h++)if(e&&c.nodeName(f[h],"script")&&(!f[h].type||f[h].type.toLowerCase()==="text/javascript"))e.push(f[h].parentNode?f[h].parentNode.removeChild(f[h]):f[h]);else{f[h].nodeType===1&&f.splice.apply(f,[h+1,0].concat(c.makeArray(f[h].getElementsByTagName("script")))); +d.appendChild(f[h])}return f},cleanData:function(a){for(var b,d,e=c.cache,f=c.event.special,h=c.support.deleteExpando,l=0,k;(k=a[l])!=null;l++)if(!(k.nodeName&&c.noData[k.nodeName.toLowerCase()]))if(d=k[c.expando]){if((b=e[d])&&b.events)for(var o in b.events)f[o]?c.event.remove(k,o):c.removeEvent(k,o,b.handle);if(h)delete k[c.expando];else k.removeAttribute&&k.removeAttribute(c.expando);delete e[d]}}});var Ea=/alpha\([^)]*\)/i,gb=/opacity=([^)]*)/,hb=/-([a-z])/ig,ib=/([A-Z])/g,Fa=/^-?\d+(?:px)?$/i, +jb=/^-?\d/,kb={position:"absolute",visibility:"hidden",display:"block"},Pa=["Left","Right"],Qa=["Top","Bottom"],W,Ga,aa,lb=function(a,b){return b.toUpperCase()};c.fn.css=function(a,b){if(arguments.length===2&&b===B)return this;return c.access(this,a,b,true,function(d,e,f){return f!==B?c.style(d,e,f):c.css(d,e)})};c.extend({cssHooks:{opacity:{get:function(a,b){if(b){var d=W(a,"opacity","opacity");return d===""?"1":d}else return a.style.opacity}}},cssNumber:{zIndex:true,fontWeight:true,opacity:true, +zoom:true,lineHeight:true},cssProps:{"float":c.support.cssFloat?"cssFloat":"styleFloat"},style:function(a,b,d,e){if(!(!a||a.nodeType===3||a.nodeType===8||!a.style)){var f,h=c.camelCase(b),l=a.style,k=c.cssHooks[h];b=c.cssProps[h]||h;if(d!==B){if(!(typeof d==="number"&&isNaN(d)||d==null)){if(typeof d==="number"&&!c.cssNumber[h])d+="px";if(!k||!("set"in k)||(d=k.set(a,d))!==B)try{l[b]=d}catch(o){}}}else{if(k&&"get"in k&&(f=k.get(a,false,e))!==B)return f;return l[b]}}},css:function(a,b,d){var e,f=c.camelCase(b), +h=c.cssHooks[f];b=c.cssProps[f]||f;if(h&&"get"in h&&(e=h.get(a,true,d))!==B)return e;else if(W)return W(a,b,f)},swap:function(a,b,d){var e={},f;for(f in b){e[f]=a.style[f];a.style[f]=b[f]}d.call(a);for(f in b)a.style[f]=e[f]},camelCase:function(a){return a.replace(hb,lb)}});c.curCSS=c.css;c.each(["height","width"],function(a,b){c.cssHooks[b]={get:function(d,e,f){var h;if(e){if(d.offsetWidth!==0)h=oa(d,b,f);else c.swap(d,kb,function(){h=oa(d,b,f)});if(h<=0){h=W(d,b,b);if(h==="0px"&&aa)h=aa(d,b,b); +if(h!=null)return h===""||h==="auto"?"0px":h}if(h<0||h==null){h=d.style[b];return h===""||h==="auto"?"0px":h}return typeof h==="string"?h:h+"px"}},set:function(d,e){if(Fa.test(e)){e=parseFloat(e);if(e>=0)return e+"px"}else return e}}});if(!c.support.opacity)c.cssHooks.opacity={get:function(a,b){return gb.test((b&&a.currentStyle?a.currentStyle.filter:a.style.filter)||"")?parseFloat(RegExp.$1)/100+"":b?"1":""},set:function(a,b){var d=a.style;d.zoom=1;var e=c.isNaN(b)?"":"alpha(opacity="+b*100+")",f= +d.filter||"";d.filter=Ea.test(f)?f.replace(Ea,e):d.filter+" "+e}};if(t.defaultView&&t.defaultView.getComputedStyle)Ga=function(a,b,d){var e;d=d.replace(ib,"-$1").toLowerCase();if(!(b=a.ownerDocument.defaultView))return B;if(b=b.getComputedStyle(a,null)){e=b.getPropertyValue(d);if(e===""&&!c.contains(a.ownerDocument.documentElement,a))e=c.style(a,d)}return e};if(t.documentElement.currentStyle)aa=function(a,b){var d,e,f=a.currentStyle&&a.currentStyle[b],h=a.style;if(!Fa.test(f)&&jb.test(f)){d=h.left; +e=a.runtimeStyle.left;a.runtimeStyle.left=a.currentStyle.left;h.left=b==="fontSize"?"1em":f||0;f=h.pixelLeft+"px";h.left=d;a.runtimeStyle.left=e}return f===""?"auto":f};W=Ga||aa;if(c.expr&&c.expr.filters){c.expr.filters.hidden=function(a){var b=a.offsetHeight;return a.offsetWidth===0&&b===0||!c.support.reliableHiddenOffsets&&(a.style.display||c.css(a,"display"))==="none"};c.expr.filters.visible=function(a){return!c.expr.filters.hidden(a)}}var mb=c.now(),nb=/)<[^<]*)*<\/script>/gi, +ob=/^(?:select|textarea)/i,pb=/^(?:color|date|datetime|email|hidden|month|number|password|range|search|tel|text|time|url|week)$/i,qb=/^(?:GET|HEAD)$/,Ra=/\[\]$/,T=/\=\?(&|$)/,ja=/\?/,rb=/([?&])_=[^&]*/,sb=/^(\w+:)?\/\/([^\/?#]+)/,tb=/%20/g,ub=/#.*$/,Ha=c.fn.load;c.fn.extend({load:function(a,b,d){if(typeof a!=="string"&&Ha)return Ha.apply(this,arguments);else if(!this.length)return this;var e=a.indexOf(" ");if(e>=0){var f=a.slice(e,a.length);a=a.slice(0,e)}e="GET";if(b)if(c.isFunction(b)){d=b;b=null}else if(typeof b=== +"object"){b=c.param(b,c.ajaxSettings.traditional);e="POST"}var h=this;c.ajax({url:a,type:e,dataType:"html",data:b,complete:function(l,k){if(k==="success"||k==="notmodified")h.html(f?c("
").append(l.responseText.replace(nb,"")).find(f):l.responseText);d&&h.each(d,[l.responseText,k,l])}});return this},serialize:function(){return c.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?c.makeArray(this.elements):this}).filter(function(){return this.name&& +!this.disabled&&(this.checked||ob.test(this.nodeName)||pb.test(this.type))}).map(function(a,b){var d=c(this).val();return d==null?null:c.isArray(d)?c.map(d,function(e){return{name:b.name,value:e}}):{name:b.name,value:d}}).get()}});c.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(a,b){c.fn[b]=function(d){return this.bind(b,d)}});c.extend({get:function(a,b,d,e){if(c.isFunction(b)){e=e||d;d=b;b=null}return c.ajax({type:"GET",url:a,data:b,success:d,dataType:e})}, +getScript:function(a,b){return c.get(a,null,b,"script")},getJSON:function(a,b,d){return c.get(a,b,d,"json")},post:function(a,b,d,e){if(c.isFunction(b)){e=e||d;d=b;b={}}return c.ajax({type:"POST",url:a,data:b,success:d,dataType:e})},ajaxSetup:function(a){c.extend(c.ajaxSettings,a)},ajaxSettings:{url:location.href,global:true,type:"GET",contentType:"application/x-www-form-urlencoded",processData:true,async:true,xhr:function(){return new E.XMLHttpRequest},accepts:{xml:"application/xml, text/xml",html:"text/html", +script:"text/javascript, application/javascript",json:"application/json, text/javascript",text:"text/plain",_default:"*/*"}},ajax:function(a){var b=c.extend(true,{},c.ajaxSettings,a),d,e,f,h=b.type.toUpperCase(),l=qb.test(h);b.url=b.url.replace(ub,"");b.context=a&&a.context!=null?a.context:b;if(b.data&&b.processData&&typeof b.data!=="string")b.data=c.param(b.data,b.traditional);if(b.dataType==="jsonp"){if(h==="GET")T.test(b.url)||(b.url+=(ja.test(b.url)?"&":"?")+(b.jsonp||"callback")+"=?");else if(!b.data|| +!T.test(b.data))b.data=(b.data?b.data+"&":"")+(b.jsonp||"callback")+"=?";b.dataType="json"}if(b.dataType==="json"&&(b.data&&T.test(b.data)||T.test(b.url))){d=b.jsonpCallback||"jsonp"+mb++;if(b.data)b.data=(b.data+"").replace(T,"="+d+"$1");b.url=b.url.replace(T,"="+d+"$1");b.dataType="script";var k=E[d];E[d]=function(m){if(c.isFunction(k))k(m);else{E[d]=B;try{delete E[d]}catch(p){}}f=m;c.handleSuccess(b,w,e,f);c.handleComplete(b,w,e,f);r&&r.removeChild(A)}}if(b.dataType==="script"&&b.cache===null)b.cache= +false;if(b.cache===false&&l){var o=c.now(),x=b.url.replace(rb,"$1_="+o);b.url=x+(x===b.url?(ja.test(b.url)?"&":"?")+"_="+o:"")}if(b.data&&l)b.url+=(ja.test(b.url)?"&":"?")+b.data;b.global&&c.active++===0&&c.event.trigger("ajaxStart");o=(o=sb.exec(b.url))&&(o[1]&&o[1].toLowerCase()!==location.protocol||o[2].toLowerCase()!==location.host);if(b.dataType==="script"&&h==="GET"&&o){var r=t.getElementsByTagName("head")[0]||t.documentElement,A=t.createElement("script");if(b.scriptCharset)A.charset=b.scriptCharset; +A.src=b.url;if(!d){var C=false;A.onload=A.onreadystatechange=function(){if(!C&&(!this.readyState||this.readyState==="loaded"||this.readyState==="complete")){C=true;c.handleSuccess(b,w,e,f);c.handleComplete(b,w,e,f);A.onload=A.onreadystatechange=null;r&&A.parentNode&&r.removeChild(A)}}}r.insertBefore(A,r.firstChild);return B}var J=false,w=b.xhr();if(w){b.username?w.open(h,b.url,b.async,b.username,b.password):w.open(h,b.url,b.async);try{if(b.data!=null&&!l||a&&a.contentType)w.setRequestHeader("Content-Type", +b.contentType);if(b.ifModified){c.lastModified[b.url]&&w.setRequestHeader("If-Modified-Since",c.lastModified[b.url]);c.etag[b.url]&&w.setRequestHeader("If-None-Match",c.etag[b.url])}o||w.setRequestHeader("X-Requested-With","XMLHttpRequest");w.setRequestHeader("Accept",b.dataType&&b.accepts[b.dataType]?b.accepts[b.dataType]+", */*; q=0.01":b.accepts._default)}catch(I){}if(b.beforeSend&&b.beforeSend.call(b.context,w,b)===false){b.global&&c.active--===1&&c.event.trigger("ajaxStop");w.abort();return false}b.global&& +c.triggerGlobal(b,"ajaxSend",[w,b]);var L=w.onreadystatechange=function(m){if(!w||w.readyState===0||m==="abort"){J||c.handleComplete(b,w,e,f);J=true;if(w)w.onreadystatechange=c.noop}else if(!J&&w&&(w.readyState===4||m==="timeout")){J=true;w.onreadystatechange=c.noop;e=m==="timeout"?"timeout":!c.httpSuccess(w)?"error":b.ifModified&&c.httpNotModified(w,b.url)?"notmodified":"success";var p;if(e==="success")try{f=c.httpData(w,b.dataType,b)}catch(q){e="parsererror";p=q}if(e==="success"||e==="notmodified")d|| +c.handleSuccess(b,w,e,f);else c.handleError(b,w,e,p);d||c.handleComplete(b,w,e,f);m==="timeout"&&w.abort();if(b.async)w=null}};try{var g=w.abort;w.abort=function(){w&&Function.prototype.call.call(g,w);L("abort")}}catch(i){}b.async&&b.timeout>0&&setTimeout(function(){w&&!J&&L("timeout")},b.timeout);try{w.send(l||b.data==null?null:b.data)}catch(n){c.handleError(b,w,null,n);c.handleComplete(b,w,e,f)}b.async||L();return w}},param:function(a,b){var d=[],e=function(h,l){l=c.isFunction(l)?l():l;d[d.length]= +encodeURIComponent(h)+"="+encodeURIComponent(l)};if(b===B)b=c.ajaxSettings.traditional;if(c.isArray(a)||a.jquery)c.each(a,function(){e(this.name,this.value)});else for(var f in a)da(f,a[f],b,e);return d.join("&").replace(tb,"+")}});c.extend({active:0,lastModified:{},etag:{},handleError:function(a,b,d,e){a.error&&a.error.call(a.context,b,d,e);a.global&&c.triggerGlobal(a,"ajaxError",[b,a,e])},handleSuccess:function(a,b,d,e){a.success&&a.success.call(a.context,e,d,b);a.global&&c.triggerGlobal(a,"ajaxSuccess", +[b,a])},handleComplete:function(a,b,d){a.complete&&a.complete.call(a.context,b,d);a.global&&c.triggerGlobal(a,"ajaxComplete",[b,a]);a.global&&c.active--===1&&c.event.trigger("ajaxStop")},triggerGlobal:function(a,b,d){(a.context&&a.context.url==null?c(a.context):c.event).trigger(b,d)},httpSuccess:function(a){try{return!a.status&&location.protocol==="file:"||a.status>=200&&a.status<300||a.status===304||a.status===1223}catch(b){}return false},httpNotModified:function(a,b){var d=a.getResponseHeader("Last-Modified"), +e=a.getResponseHeader("Etag");if(d)c.lastModified[b]=d;if(e)c.etag[b]=e;return a.status===304},httpData:function(a,b,d){var e=a.getResponseHeader("content-type")||"",f=b==="xml"||!b&&e.indexOf("xml")>=0;a=f?a.responseXML:a.responseText;f&&a.documentElement.nodeName==="parsererror"&&c.error("parsererror");if(d&&d.dataFilter)a=d.dataFilter(a,b);if(typeof a==="string")if(b==="json"||!b&&e.indexOf("json")>=0)a=c.parseJSON(a);else if(b==="script"||!b&&e.indexOf("javascript")>=0)c.globalEval(a);return a}}); +if(E.ActiveXObject)c.ajaxSettings.xhr=function(){if(E.location.protocol!=="file:")try{return new E.XMLHttpRequest}catch(a){}try{return new E.ActiveXObject("Microsoft.XMLHTTP")}catch(b){}};c.support.ajax=!!c.ajaxSettings.xhr();var ea={},vb=/^(?:toggle|show|hide)$/,wb=/^([+\-]=)?([\d+.\-]+)(.*)$/,ba,pa=[["height","marginTop","marginBottom","paddingTop","paddingBottom"],["width","marginLeft","marginRight","paddingLeft","paddingRight"],["opacity"]];c.fn.extend({show:function(a,b,d){if(a||a===0)return this.animate(S("show", +3),a,b,d);else{d=0;for(var e=this.length;d=0;e--)if(d[e].elem===this){b&&d[e](true);d.splice(e,1)}});b||this.dequeue();return this}});c.each({slideDown:S("show",1),slideUp:S("hide",1),slideToggle:S("toggle",1),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(a,b){c.fn[a]=function(d,e,f){return this.animate(b, +d,e,f)}});c.extend({speed:function(a,b,d){var e=a&&typeof a==="object"?c.extend({},a):{complete:d||!d&&b||c.isFunction(a)&&a,duration:a,easing:d&&b||b&&!c.isFunction(b)&&b};e.duration=c.fx.off?0:typeof e.duration==="number"?e.duration:e.duration in c.fx.speeds?c.fx.speeds[e.duration]:c.fx.speeds._default;e.old=e.complete;e.complete=function(){e.queue!==false&&c(this).dequeue();c.isFunction(e.old)&&e.old.call(this)};return e},easing:{linear:function(a,b,d,e){return d+e*a},swing:function(a,b,d,e){return(-Math.cos(a* +Math.PI)/2+0.5)*e+d}},timers:[],fx:function(a,b,d){this.options=b;this.elem=a;this.prop=d;if(!b.orig)b.orig={}}});c.fx.prototype={update:function(){this.options.step&&this.options.step.call(this.elem,this.now,this);(c.fx.step[this.prop]||c.fx.step._default)(this)},cur:function(){if(this.elem[this.prop]!=null&&(!this.elem.style||this.elem.style[this.prop]==null))return this.elem[this.prop];var a=parseFloat(c.css(this.elem,this.prop));return a&&a>-1E4?a:0},custom:function(a,b,d){function e(l){return f.step(l)} +var f=this,h=c.fx;this.startTime=c.now();this.start=a;this.end=b;this.unit=d||this.unit||"px";this.now=this.start;this.pos=this.state=0;e.elem=this.elem;if(e()&&c.timers.push(e)&&!ba)ba=setInterval(h.tick,h.interval)},show:function(){this.options.orig[this.prop]=c.style(this.elem,this.prop);this.options.show=true;this.custom(this.prop==="width"||this.prop==="height"?1:0,this.cur());c(this.elem).show()},hide:function(){this.options.orig[this.prop]=c.style(this.elem,this.prop);this.options.hide=true; +this.custom(this.cur(),0)},step:function(a){var b=c.now(),d=true;if(a||b>=this.options.duration+this.startTime){this.now=this.end;this.pos=this.state=1;this.update();this.options.curAnim[this.prop]=true;for(var e in this.options.curAnim)if(this.options.curAnim[e]!==true)d=false;if(d){if(this.options.overflow!=null&&!c.support.shrinkWrapBlocks){var f=this.elem,h=this.options;c.each(["","X","Y"],function(k,o){f.style["overflow"+o]=h.overflow[k]})}this.options.hide&&c(this.elem).hide();if(this.options.hide|| +this.options.show)for(var l in this.options.curAnim)c.style(this.elem,l,this.options.orig[l]);this.options.complete.call(this.elem)}return false}else{a=b-this.startTime;this.state=a/this.options.duration;b=this.options.easing||(c.easing.swing?"swing":"linear");this.pos=c.easing[this.options.specialEasing&&this.options.specialEasing[this.prop]||b](this.state,a,0,1,this.options.duration);this.now=this.start+(this.end-this.start)*this.pos;this.update()}return true}};c.extend(c.fx,{tick:function(){for(var a= +c.timers,b=0;b-1;e={};var x={};if(o)x=f.position();l=o?x.top:parseInt(l,10)||0;k=o?x.left:parseInt(k,10)||0;if(c.isFunction(b))b=b.call(a,d,h);if(b.top!=null)e.top=b.top-h.top+l;if(b.left!=null)e.left=b.left-h.left+k;"using"in b?b.using.call(a, +e):f.css(e)}};c.fn.extend({position:function(){if(!this[0])return null;var a=this[0],b=this.offsetParent(),d=this.offset(),e=Ia.test(b[0].nodeName)?{top:0,left:0}:b.offset();d.top-=parseFloat(c.css(a,"marginTop"))||0;d.left-=parseFloat(c.css(a,"marginLeft"))||0;e.top+=parseFloat(c.css(b[0],"borderTopWidth"))||0;e.left+=parseFloat(c.css(b[0],"borderLeftWidth"))||0;return{top:d.top-e.top,left:d.left-e.left}},offsetParent:function(){return this.map(function(){for(var a=this.offsetParent||t.body;a&&!Ia.test(a.nodeName)&& +c.css(a,"position")==="static";)a=a.offsetParent;return a})}});c.each(["Left","Top"],function(a,b){var d="scroll"+b;c.fn[d]=function(e){var f=this[0],h;if(!f)return null;if(e!==B)return this.each(function(){if(h=fa(this))h.scrollTo(!a?e:c(h).scrollLeft(),a?e:c(h).scrollTop());else this[d]=e});else return(h=fa(f))?"pageXOffset"in h?h[a?"pageYOffset":"pageXOffset"]:c.support.boxModel&&h.document.documentElement[d]||h.document.body[d]:f[d]}});c.each(["Height","Width"],function(a,b){var d=b.toLowerCase(); +c.fn["inner"+b]=function(){return this[0]?parseFloat(c.css(this[0],d,"padding")):null};c.fn["outer"+b]=function(e){return this[0]?parseFloat(c.css(this[0],d,e?"margin":"border")):null};c.fn[d]=function(e){var f=this[0];if(!f)return e==null?null:this;if(c.isFunction(e))return this.each(function(l){var k=c(this);k[d](e.call(this,l,k[d]()))});if(c.isWindow(f))return f.document.compatMode==="CSS1Compat"&&f.document.documentElement["client"+b]||f.document.body["client"+b];else if(f.nodeType===9)return Math.max(f.documentElement["client"+ +b],f.body["scroll"+b],f.documentElement["scroll"+b],f.body["offset"+b],f.documentElement["offset"+b]);else if(e===B){f=c.css(f,d);var h=parseFloat(f);return c.isNaN(h)?f:h}else return this.css(d,typeof e==="string"?e:e+"px")}})})(window); diff --git a/sources/www/jquery/jquery-ui-1.8.7.custom.min.js b/sources/www/jquery/jquery-ui-1.8.7.custom.min.js new file mode 100644 index 0000000..b03a87e --- /dev/null +++ b/sources/www/jquery/jquery-ui-1.8.7.custom.min.js @@ -0,0 +1,781 @@ +/*! + * jQuery UI 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI + */ +(function(c,j){function k(a){return!c(a).parents().andSelf().filter(function(){return c.curCSS(this,"visibility")==="hidden"||c.expr.filters.hidden(this)}).length}c.ui=c.ui||{};if(!c.ui.version){c.extend(c.ui,{version:"1.8.7",keyCode:{ALT:18,BACKSPACE:8,CAPS_LOCK:20,COMMA:188,COMMAND:91,COMMAND_LEFT:91,COMMAND_RIGHT:93,CONTROL:17,DELETE:46,DOWN:40,END:35,ENTER:13,ESCAPE:27,HOME:36,INSERT:45,LEFT:37,MENU:93,NUMPAD_ADD:107,NUMPAD_DECIMAL:110,NUMPAD_DIVIDE:111,NUMPAD_ENTER:108,NUMPAD_MULTIPLY:106, +NUMPAD_SUBTRACT:109,PAGE_DOWN:34,PAGE_UP:33,PERIOD:190,RIGHT:39,SHIFT:16,SPACE:32,TAB:9,UP:38,WINDOWS:91}});c.fn.extend({_focus:c.fn.focus,focus:function(a,b){return typeof a==="number"?this.each(function(){var d=this;setTimeout(function(){c(d).focus();b&&b.call(d)},a)}):this._focus.apply(this,arguments)},scrollParent:function(){var a;a=c.browser.msie&&/(static|relative)/.test(this.css("position"))||/absolute/.test(this.css("position"))?this.parents().filter(function(){return/(relative|absolute|fixed)/.test(c.curCSS(this, +"position",1))&&/(auto|scroll)/.test(c.curCSS(this,"overflow",1)+c.curCSS(this,"overflow-y",1)+c.curCSS(this,"overflow-x",1))}).eq(0):this.parents().filter(function(){return/(auto|scroll)/.test(c.curCSS(this,"overflow",1)+c.curCSS(this,"overflow-y",1)+c.curCSS(this,"overflow-x",1))}).eq(0);return/fixed/.test(this.css("position"))||!a.length?c(document):a},zIndex:function(a){if(a!==j)return this.css("zIndex",a);if(this.length){a=c(this[0]);for(var b;a.length&&a[0]!==document;){b=a.css("position"); +if(b==="absolute"||b==="relative"||b==="fixed"){b=parseInt(a.css("zIndex"),10);if(!isNaN(b)&&b!==0)return b}a=a.parent()}}return 0},disableSelection:function(){return this.bind((c.support.selectstart?"selectstart":"mousedown")+".ui-disableSelection",function(a){a.preventDefault()})},enableSelection:function(){return this.unbind(".ui-disableSelection")}});c.each(["Width","Height"],function(a,b){function d(f,g,l,m){c.each(e,function(){g-=parseFloat(c.curCSS(f,"padding"+this,true))||0;if(l)g-=parseFloat(c.curCSS(f, +"border"+this+"Width",true))||0;if(m)g-=parseFloat(c.curCSS(f,"margin"+this,true))||0});return g}var e=b==="Width"?["Left","Right"]:["Top","Bottom"],h=b.toLowerCase(),i={innerWidth:c.fn.innerWidth,innerHeight:c.fn.innerHeight,outerWidth:c.fn.outerWidth,outerHeight:c.fn.outerHeight};c.fn["inner"+b]=function(f){if(f===j)return i["inner"+b].call(this);return this.each(function(){c(this).css(h,d(this,f)+"px")})};c.fn["outer"+b]=function(f,g){if(typeof f!=="number")return i["outer"+b].call(this,f);return this.each(function(){c(this).css(h, +d(this,f,true,g)+"px")})}});c.extend(c.expr[":"],{data:function(a,b,d){return!!c.data(a,d[3])},focusable:function(a){var b=a.nodeName.toLowerCase(),d=c.attr(a,"tabindex");if("area"===b){b=a.parentNode;d=b.name;if(!a.href||!d||b.nodeName.toLowerCase()!=="map")return false;a=c("img[usemap=#"+d+"]")[0];return!!a&&k(a)}return(/input|select|textarea|button|object/.test(b)?!a.disabled:"a"==b?a.href||!isNaN(d):!isNaN(d))&&k(a)},tabbable:function(a){var b=c.attr(a,"tabindex");return(isNaN(b)||b>=0)&&c(a).is(":focusable")}}); +c(function(){var a=document.body,b=a.appendChild(b=document.createElement("div"));c.extend(b.style,{minHeight:"100px",height:"auto",padding:0,borderWidth:0});c.support.minHeight=b.offsetHeight===100;c.support.selectstart="onselectstart"in b;a.removeChild(b).style.display="none"});c.extend(c.ui,{plugin:{add:function(a,b,d){a=c.ui[a].prototype;for(var e in d){a.plugins[e]=a.plugins[e]||[];a.plugins[e].push([b,d[e]])}},call:function(a,b,d){if((b=a.plugins[b])&&a.element[0].parentNode)for(var e=0;e0)return true;a[b]=1;d=a[b]>0;a[b]=0;return d},isOverAxis:function(a,b,d){return a>b&&a=9)&&!a.button)return this._mouseUp(a);if(this._mouseStarted){this._mouseDrag(a); +return a.preventDefault()}if(this._mouseDistanceMet(a)&&this._mouseDelayMet(a))(this._mouseStarted=this._mouseStart(this._mouseDownEvent,a)!==false)?this._mouseDrag(a):this._mouseUp(a);return!this._mouseStarted},_mouseUp:function(a){c(document).unbind("mousemove."+this.widgetName,this._mouseMoveDelegate).unbind("mouseup."+this.widgetName,this._mouseUpDelegate);if(this._mouseStarted){this._mouseStarted=false;a.target==this._mouseDownEvent.target&&c.data(a.target,this.widgetName+".preventClickEvent", +true);this._mouseStop(a)}return false},_mouseDistanceMet:function(a){return Math.max(Math.abs(this._mouseDownEvent.pageX-a.pageX),Math.abs(this._mouseDownEvent.pageY-a.pageY))>=this.options.distance},_mouseDelayMet:function(){return this.mouseDelayMet},_mouseStart:function(){},_mouseDrag:function(){},_mouseStop:function(){},_mouseCapture:function(){return true}})})(jQuery); +;/* + * jQuery UI Position 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Position + */ +(function(c){c.ui=c.ui||{};var n=/left|center|right/,o=/top|center|bottom/,t=c.fn.position,u=c.fn.offset;c.fn.position=function(b){if(!b||!b.of)return t.apply(this,arguments);b=c.extend({},b);var a=c(b.of),d=a[0],g=(b.collision||"flip").split(" "),e=b.offset?b.offset.split(" "):[0,0],h,k,j;if(d.nodeType===9){h=a.width();k=a.height();j={top:0,left:0}}else if(d.setTimeout){h=a.width();k=a.height();j={top:a.scrollTop(),left:a.scrollLeft()}}else if(d.preventDefault){b.at="left top";h=k=0;j={top:b.of.pageY, +left:b.of.pageX}}else{h=a.outerWidth();k=a.outerHeight();j=a.offset()}c.each(["my","at"],function(){var f=(b[this]||"").split(" ");if(f.length===1)f=n.test(f[0])?f.concat(["center"]):o.test(f[0])?["center"].concat(f):["center","center"];f[0]=n.test(f[0])?f[0]:"center";f[1]=o.test(f[1])?f[1]:"center";b[this]=f});if(g.length===1)g[1]=g[0];e[0]=parseInt(e[0],10)||0;if(e.length===1)e[1]=e[0];e[1]=parseInt(e[1],10)||0;if(b.at[0]==="right")j.left+=h;else if(b.at[0]==="center")j.left+=h/2;if(b.at[1]==="bottom")j.top+= +k;else if(b.at[1]==="center")j.top+=k/2;j.left+=e[0];j.top+=e[1];return this.each(function(){var f=c(this),l=f.outerWidth(),m=f.outerHeight(),p=parseInt(c.curCSS(this,"marginLeft",true))||0,q=parseInt(c.curCSS(this,"marginTop",true))||0,v=l+p+parseInt(c.curCSS(this,"marginRight",true))||0,w=m+q+parseInt(c.curCSS(this,"marginBottom",true))||0,i=c.extend({},j),r;if(b.my[0]==="right")i.left-=l;else if(b.my[0]==="center")i.left-=l/2;if(b.my[1]==="bottom")i.top-=m;else if(b.my[1]==="center")i.top-=m/2; +i.left=Math.round(i.left);i.top=Math.round(i.top);r={left:i.left-p,top:i.top-q};c.each(["left","top"],function(s,x){c.ui.position[g[s]]&&c.ui.position[g[s]][x](i,{targetWidth:h,targetHeight:k,elemWidth:l,elemHeight:m,collisionPosition:r,collisionWidth:v,collisionHeight:w,offset:e,my:b.my,at:b.at})});c.fn.bgiframe&&f.bgiframe();f.offset(c.extend(i,{using:b.using}))})};c.ui.position={fit:{left:function(b,a){var d=c(window);d=a.collisionPosition.left+a.collisionWidth-d.width()-d.scrollLeft();b.left= +d>0?b.left-d:Math.max(b.left-a.collisionPosition.left,b.left)},top:function(b,a){var d=c(window);d=a.collisionPosition.top+a.collisionHeight-d.height()-d.scrollTop();b.top=d>0?b.top-d:Math.max(b.top-a.collisionPosition.top,b.top)}},flip:{left:function(b,a){if(a.at[0]!=="center"){var d=c(window);d=a.collisionPosition.left+a.collisionWidth-d.width()-d.scrollLeft();var g=a.my[0]==="left"?-a.elemWidth:a.my[0]==="right"?a.elemWidth:0,e=a.at[0]==="left"?a.targetWidth:-a.targetWidth,h=-2*a.offset[0];b.left+= +a.collisionPosition.left<0?g+e+h:d>0?g+e+h:0}},top:function(b,a){if(a.at[1]!=="center"){var d=c(window);d=a.collisionPosition.top+a.collisionHeight-d.height()-d.scrollTop();var g=a.my[1]==="top"?-a.elemHeight:a.my[1]==="bottom"?a.elemHeight:0,e=a.at[1]==="top"?a.targetHeight:-a.targetHeight,h=-2*a.offset[1];b.top+=a.collisionPosition.top<0?g+e+h:d>0?g+e+h:0}}}};if(!c.offset.setOffset){c.offset.setOffset=function(b,a){if(/static/.test(c.curCSS(b,"position")))b.style.position="relative";var d=c(b), +g=d.offset(),e=parseInt(c.curCSS(b,"top",true),10)||0,h=parseInt(c.curCSS(b,"left",true),10)||0;g={top:a.top-g.top+e,left:a.left-g.left+h};"using"in a?a.using.call(b,g):d.css(g)};c.fn.offset=function(b){var a=this[0];if(!a||!a.ownerDocument)return null;if(b)return this.each(function(){c.offset.setOffset(this,b)});return u.call(this)}}})(jQuery); +;/* + * jQuery UI Draggable 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Draggables + * + * Depends: + * jquery.ui.core.js + * jquery.ui.mouse.js + * jquery.ui.widget.js + */ +(function(d){d.widget("ui.draggable",d.ui.mouse,{widgetEventPrefix:"drag",options:{addClasses:true,appendTo:"parent",axis:false,connectToSortable:false,containment:false,cursor:"auto",cursorAt:false,grid:false,handle:false,helper:"original",iframeFix:false,opacity:false,refreshPositions:false,revert:false,revertDuration:500,scope:"default",scroll:true,scrollSensitivity:20,scrollSpeed:20,snap:false,snapMode:"both",snapTolerance:20,stack:false,zIndex:false},_create:function(){if(this.options.helper== +"original"&&!/^(?:r|a|f)/.test(this.element.css("position")))this.element[0].style.position="relative";this.options.addClasses&&this.element.addClass("ui-draggable");this.options.disabled&&this.element.addClass("ui-draggable-disabled");this._mouseInit()},destroy:function(){if(this.element.data("draggable")){this.element.removeData("draggable").unbind(".draggable").removeClass("ui-draggable ui-draggable-dragging ui-draggable-disabled");this._mouseDestroy();return this}},_mouseCapture:function(a){var b= +this.options;if(this.helper||b.disabled||d(a.target).is(".ui-resizable-handle"))return false;this.handle=this._getHandle(a);if(!this.handle)return false;return true},_mouseStart:function(a){var b=this.options;this.helper=this._createHelper(a);this._cacheHelperProportions();if(d.ui.ddmanager)d.ui.ddmanager.current=this;this._cacheMargins();this.cssPosition=this.helper.css("position");this.scrollParent=this.helper.scrollParent();this.offset=this.positionAbs=this.element.offset();this.offset={top:this.offset.top- +this.margins.top,left:this.offset.left-this.margins.left};d.extend(this.offset,{click:{left:a.pageX-this.offset.left,top:a.pageY-this.offset.top},parent:this._getParentOffset(),relative:this._getRelativeOffset()});this.originalPosition=this.position=this._generatePosition(a);this.originalPageX=a.pageX;this.originalPageY=a.pageY;b.cursorAt&&this._adjustOffsetFromHelper(b.cursorAt);b.containment&&this._setContainment();if(this._trigger("start",a)===false){this._clear();return false}this._cacheHelperProportions(); +d.ui.ddmanager&&!b.dropBehaviour&&d.ui.ddmanager.prepareOffsets(this,a);this.helper.addClass("ui-draggable-dragging");this._mouseDrag(a,true);return true},_mouseDrag:function(a,b){this.position=this._generatePosition(a);this.positionAbs=this._convertPositionTo("absolute");if(!b){b=this._uiHash();if(this._trigger("drag",a,b)===false){this._mouseUp({});return false}this.position=b.position}if(!this.options.axis||this.options.axis!="y")this.helper[0].style.left=this.position.left+"px";if(!this.options.axis|| +this.options.axis!="x")this.helper[0].style.top=this.position.top+"px";d.ui.ddmanager&&d.ui.ddmanager.drag(this,a);return false},_mouseStop:function(a){var b=false;if(d.ui.ddmanager&&!this.options.dropBehaviour)b=d.ui.ddmanager.drop(this,a);if(this.dropped){b=this.dropped;this.dropped=false}if(!this.element[0]||!this.element[0].parentNode)return false;if(this.options.revert=="invalid"&&!b||this.options.revert=="valid"&&b||this.options.revert===true||d.isFunction(this.options.revert)&&this.options.revert.call(this.element, +b)){var c=this;d(this.helper).animate(this.originalPosition,parseInt(this.options.revertDuration,10),function(){c._trigger("stop",a)!==false&&c._clear()})}else this._trigger("stop",a)!==false&&this._clear();return false},cancel:function(){this.helper.is(".ui-draggable-dragging")?this._mouseUp({}):this._clear();return this},_getHandle:function(a){var b=!this.options.handle||!d(this.options.handle,this.element).length?true:false;d(this.options.handle,this.element).find("*").andSelf().each(function(){if(this== +a.target)b=true});return b},_createHelper:function(a){var b=this.options;a=d.isFunction(b.helper)?d(b.helper.apply(this.element[0],[a])):b.helper=="clone"?this.element.clone():this.element;a.parents("body").length||a.appendTo(b.appendTo=="parent"?this.element[0].parentNode:b.appendTo);a[0]!=this.element[0]&&!/(fixed|absolute)/.test(a.css("position"))&&a.css("position","absolute");return a},_adjustOffsetFromHelper:function(a){if(typeof a=="string")a=a.split(" ");if(d.isArray(a))a={left:+a[0],top:+a[1]|| +0};if("left"in a)this.offset.click.left=a.left+this.margins.left;if("right"in a)this.offset.click.left=this.helperProportions.width-a.right+this.margins.left;if("top"in a)this.offset.click.top=a.top+this.margins.top;if("bottom"in a)this.offset.click.top=this.helperProportions.height-a.bottom+this.margins.top},_getParentOffset:function(){this.offsetParent=this.helper.offsetParent();var a=this.offsetParent.offset();if(this.cssPosition=="absolute"&&this.scrollParent[0]!=document&&d.ui.contains(this.scrollParent[0], +this.offsetParent[0])){a.left+=this.scrollParent.scrollLeft();a.top+=this.scrollParent.scrollTop()}if(this.offsetParent[0]==document.body||this.offsetParent[0].tagName&&this.offsetParent[0].tagName.toLowerCase()=="html"&&d.browser.msie)a={top:0,left:0};return{top:a.top+(parseInt(this.offsetParent.css("borderTopWidth"),10)||0),left:a.left+(parseInt(this.offsetParent.css("borderLeftWidth"),10)||0)}},_getRelativeOffset:function(){if(this.cssPosition=="relative"){var a=this.element.position();return{top:a.top- +(parseInt(this.helper.css("top"),10)||0)+this.scrollParent.scrollTop(),left:a.left-(parseInt(this.helper.css("left"),10)||0)+this.scrollParent.scrollLeft()}}else return{top:0,left:0}},_cacheMargins:function(){this.margins={left:parseInt(this.element.css("marginLeft"),10)||0,top:parseInt(this.element.css("marginTop"),10)||0}},_cacheHelperProportions:function(){this.helperProportions={width:this.helper.outerWidth(),height:this.helper.outerHeight()}},_setContainment:function(){var a=this.options;if(a.containment== +"parent")a.containment=this.helper[0].parentNode;if(a.containment=="document"||a.containment=="window")this.containment=[(a.containment=="document"?0:d(window).scrollLeft())-this.offset.relative.left-this.offset.parent.left,(a.containment=="document"?0:d(window).scrollTop())-this.offset.relative.top-this.offset.parent.top,(a.containment=="document"?0:d(window).scrollLeft())+d(a.containment=="document"?document:window).width()-this.helperProportions.width-this.margins.left,(a.containment=="document"? +0:d(window).scrollTop())+(d(a.containment=="document"?document:window).height()||document.body.parentNode.scrollHeight)-this.helperProportions.height-this.margins.top];if(!/^(document|window|parent)$/.test(a.containment)&&a.containment.constructor!=Array){var b=d(a.containment)[0];if(b){a=d(a.containment).offset();var c=d(b).css("overflow")!="hidden";this.containment=[a.left+(parseInt(d(b).css("borderLeftWidth"),10)||0)+(parseInt(d(b).css("paddingLeft"),10)||0)-this.margins.left,a.top+(parseInt(d(b).css("borderTopWidth"), +10)||0)+(parseInt(d(b).css("paddingTop"),10)||0)-this.margins.top,a.left+(c?Math.max(b.scrollWidth,b.offsetWidth):b.offsetWidth)-(parseInt(d(b).css("borderLeftWidth"),10)||0)-(parseInt(d(b).css("paddingRight"),10)||0)-this.helperProportions.width-this.margins.left,a.top+(c?Math.max(b.scrollHeight,b.offsetHeight):b.offsetHeight)-(parseInt(d(b).css("borderTopWidth"),10)||0)-(parseInt(d(b).css("paddingBottom"),10)||0)-this.helperProportions.height-this.margins.top]}}else if(a.containment.constructor== +Array)this.containment=a.containment},_convertPositionTo:function(a,b){if(!b)b=this.position;a=a=="absolute"?1:-1;var c=this.cssPosition=="absolute"&&!(this.scrollParent[0]!=document&&d.ui.contains(this.scrollParent[0],this.offsetParent[0]))?this.offsetParent:this.scrollParent,f=/(html|body)/i.test(c[0].tagName);return{top:b.top+this.offset.relative.top*a+this.offset.parent.top*a-(d.browser.safari&&d.browser.version<526&&this.cssPosition=="fixed"?0:(this.cssPosition=="fixed"?-this.scrollParent.scrollTop(): +f?0:c.scrollTop())*a),left:b.left+this.offset.relative.left*a+this.offset.parent.left*a-(d.browser.safari&&d.browser.version<526&&this.cssPosition=="fixed"?0:(this.cssPosition=="fixed"?-this.scrollParent.scrollLeft():f?0:c.scrollLeft())*a)}},_generatePosition:function(a){var b=this.options,c=this.cssPosition=="absolute"&&!(this.scrollParent[0]!=document&&d.ui.contains(this.scrollParent[0],this.offsetParent[0]))?this.offsetParent:this.scrollParent,f=/(html|body)/i.test(c[0].tagName),e=a.pageX,g=a.pageY; +if(this.originalPosition){if(this.containment){if(a.pageX-this.offset.click.leftthis.containment[2])e=this.containment[2]+this.offset.click.left;if(a.pageY-this.offset.click.top>this.containment[3])g=this.containment[3]+this.offset.click.top}if(b.grid){g=this.originalPageY+Math.round((g-this.originalPageY)/ +b.grid[1])*b.grid[1];g=this.containment?!(g-this.offset.click.topthis.containment[3])?g:!(g-this.offset.click.topthis.containment[2])?e:!(e-this.offset.click.left
').css({width:this.offsetWidth+"px",height:this.offsetHeight+"px",position:"absolute",opacity:"0.001",zIndex:1E3}).css(d(this).offset()).appendTo("body")})}, +stop:function(){d("div.ui-draggable-iframeFix").each(function(){this.parentNode.removeChild(this)})}});d.ui.plugin.add("draggable","opacity",{start:function(a,b){a=d(b.helper);b=d(this).data("draggable").options;if(a.css("opacity"))b._opacity=a.css("opacity");a.css("opacity",b.opacity)},stop:function(a,b){a=d(this).data("draggable").options;a._opacity&&d(b.helper).css("opacity",a._opacity)}});d.ui.plugin.add("draggable","scroll",{start:function(){var a=d(this).data("draggable");if(a.scrollParent[0]!= +document&&a.scrollParent[0].tagName!="HTML")a.overflowOffset=a.scrollParent.offset()},drag:function(a){var b=d(this).data("draggable"),c=b.options,f=false;if(b.scrollParent[0]!=document&&b.scrollParent[0].tagName!="HTML"){if(!c.axis||c.axis!="x")if(b.overflowOffset.top+b.scrollParent[0].offsetHeight-a.pageY=0;h--){var i=c.snapElements[h].left,k=i+c.snapElements[h].width,j=c.snapElements[h].top,l=j+c.snapElements[h].height;if(i-e=j&&f<=l||h>=j&&h<=l||fl)&&(e>= +i&&e<=k||g>=i&&g<=k||ek);default:return false}};d.ui.ddmanager={current:null,droppables:{"default":[]},prepareOffsets:function(a,b){var c=d.ui.ddmanager.droppables[a.options.scope]||[],e=b?b.type:null,g=(a.currentItem||a.element).find(":data(droppable)").andSelf(),f=0;a:for(;f').css({position:this.element.css("position"),width:this.element.outerWidth(),height:this.element.outerHeight(), +top:this.element.css("top"),left:this.element.css("left")}));this.element=this.element.parent().data("resizable",this.element.data("resizable"));this.elementIsWrapper=true;this.element.css({marginLeft:this.originalElement.css("marginLeft"),marginTop:this.originalElement.css("marginTop"),marginRight:this.originalElement.css("marginRight"),marginBottom:this.originalElement.css("marginBottom")});this.originalElement.css({marginLeft:0,marginTop:0,marginRight:0,marginBottom:0});this.originalResizeStyle= +this.originalElement.css("resize");this.originalElement.css("resize","none");this._proportionallyResizeElements.push(this.originalElement.css({position:"static",zoom:1,display:"block"}));this.originalElement.css({margin:this.originalElement.css("margin")});this._proportionallyResize()}this.handles=a.handles||(!e(".ui-resizable-handle",this.element).length?"e,s,se":{n:".ui-resizable-n",e:".ui-resizable-e",s:".ui-resizable-s",w:".ui-resizable-w",se:".ui-resizable-se",sw:".ui-resizable-sw",ne:".ui-resizable-ne", +nw:".ui-resizable-nw"});if(this.handles.constructor==String){if(this.handles=="all")this.handles="n,e,s,w,se,sw,ne,nw";var c=this.handles.split(",");this.handles={};for(var d=0;d');/sw|se|ne|nw/.test(f)&&g.css({zIndex:++a.zIndex});"se"==f&&g.addClass("ui-icon ui-icon-gripsmall-diagonal-se");this.handles[f]=".ui-resizable-"+f;this.element.append(g)}}this._renderAxis=function(h){h=h||this.element;for(var i in this.handles){if(this.handles[i].constructor== +String)this.handles[i]=e(this.handles[i],this.element).show();if(this.elementIsWrapper&&this.originalElement[0].nodeName.match(/textarea|input|select|button/i)){var j=e(this.handles[i],this.element),k=0;k=/sw|ne|nw|se|n|s/.test(i)?j.outerHeight():j.outerWidth();j=["padding",/ne|nw|n/.test(i)?"Top":/se|sw|s/.test(i)?"Bottom":/^e$/.test(i)?"Right":"Left"].join("");h.css(j,k);this._proportionallyResize()}e(this.handles[i])}};this._renderAxis(this.element);this._handles=e(".ui-resizable-handle",this.element).disableSelection(); +this._handles.mouseover(function(){if(!b.resizing){if(this.className)var h=this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i);b.axis=h&&h[1]?h[1]:"se"}});if(a.autoHide){this._handles.hide();e(this.element).addClass("ui-resizable-autohide").hover(function(){e(this).removeClass("ui-resizable-autohide");b._handles.show()},function(){if(!b.resizing){e(this).addClass("ui-resizable-autohide");b._handles.hide()}})}this._mouseInit()},destroy:function(){this._mouseDestroy();var b=function(c){e(c).removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing").removeData("resizable").unbind(".resizable").find(".ui-resizable-handle").remove()}; +if(this.elementIsWrapper){b(this.element);var a=this.element;a.after(this.originalElement.css({position:a.css("position"),width:a.outerWidth(),height:a.outerHeight(),top:a.css("top"),left:a.css("left")})).remove()}this.originalElement.css("resize",this.originalResizeStyle);b(this.originalElement);return this},_mouseCapture:function(b){var a=false;for(var c in this.handles)if(e(this.handles[c])[0]==b.target)a=true;return!this.options.disabled&&a},_mouseStart:function(b){var a=this.options,c=this.element.position(), +d=this.element;this.resizing=true;this.documentScroll={top:e(document).scrollTop(),left:e(document).scrollLeft()};if(d.is(".ui-draggable")||/absolute/.test(d.css("position")))d.css({position:"absolute",top:c.top,left:c.left});e.browser.opera&&/relative/.test(d.css("position"))&&d.css({position:"relative",top:"auto",left:"auto"});this._renderProxy();c=m(this.helper.css("left"));var f=m(this.helper.css("top"));if(a.containment){c+=e(a.containment).scrollLeft()||0;f+=e(a.containment).scrollTop()||0}this.offset= +this.helper.offset();this.position={left:c,top:f};this.size=this._helper?{width:d.outerWidth(),height:d.outerHeight()}:{width:d.width(),height:d.height()};this.originalSize=this._helper?{width:d.outerWidth(),height:d.outerHeight()}:{width:d.width(),height:d.height()};this.originalPosition={left:c,top:f};this.sizeDiff={width:d.outerWidth()-d.width(),height:d.outerHeight()-d.height()};this.originalMousePosition={left:b.pageX,top:b.pageY};this.aspectRatio=typeof a.aspectRatio=="number"?a.aspectRatio: +this.originalSize.width/this.originalSize.height||1;a=e(".ui-resizable-"+this.axis).css("cursor");e("body").css("cursor",a=="auto"?this.axis+"-resize":a);d.addClass("ui-resizable-resizing");this._propagate("start",b);return true},_mouseDrag:function(b){var a=this.helper,c=this.originalMousePosition,d=this._change[this.axis];if(!d)return false;c=d.apply(this,[b,b.pageX-c.left||0,b.pageY-c.top||0]);if(this._aspectRatio||b.shiftKey)c=this._updateRatio(c,b);c=this._respectSize(c,b);this._propagate("resize", +b);a.css({top:this.position.top+"px",left:this.position.left+"px",width:this.size.width+"px",height:this.size.height+"px"});!this._helper&&this._proportionallyResizeElements.length&&this._proportionallyResize();this._updateCache(c);this._trigger("resize",b,this.ui());return false},_mouseStop:function(b){this.resizing=false;var a=this.options,c=this;if(this._helper){var d=this._proportionallyResizeElements,f=d.length&&/textarea/i.test(d[0].nodeName);d=f&&e.ui.hasScroll(d[0],"left")?0:c.sizeDiff.height; +f={width:c.size.width-(f?0:c.sizeDiff.width),height:c.size.height-d};d=parseInt(c.element.css("left"),10)+(c.position.left-c.originalPosition.left)||null;var g=parseInt(c.element.css("top"),10)+(c.position.top-c.originalPosition.top)||null;a.animate||this.element.css(e.extend(f,{top:g,left:d}));c.helper.height(c.size.height);c.helper.width(c.size.width);this._helper&&!a.animate&&this._proportionallyResize()}e("body").css("cursor","auto");this.element.removeClass("ui-resizable-resizing");this._propagate("stop", +b);this._helper&&this.helper.remove();return false},_updateCache:function(b){this.offset=this.helper.offset();if(l(b.left))this.position.left=b.left;if(l(b.top))this.position.top=b.top;if(l(b.height))this.size.height=b.height;if(l(b.width))this.size.width=b.width},_updateRatio:function(b){var a=this.position,c=this.size,d=this.axis;if(b.height)b.width=c.height*this.aspectRatio;else if(b.width)b.height=c.width/this.aspectRatio;if(d=="sw"){b.left=a.left+(c.width-b.width);b.top=null}if(d=="nw"){b.top= +a.top+(c.height-b.height);b.left=a.left+(c.width-b.width)}return b},_respectSize:function(b){var a=this.options,c=this.axis,d=l(b.width)&&a.maxWidth&&a.maxWidthb.width,h=l(b.height)&&a.minHeight&&a.minHeight>b.height;if(g)b.width=a.minWidth;if(h)b.height=a.minHeight;if(d)b.width=a.maxWidth;if(f)b.height=a.maxHeight;var i=this.originalPosition.left+this.originalSize.width,j=this.position.top+this.size.height, +k=/sw|nw|w/.test(c);c=/nw|ne|n/.test(c);if(g&&k)b.left=i-a.minWidth;if(d&&k)b.left=i-a.maxWidth;if(h&&c)b.top=j-a.minHeight;if(f&&c)b.top=j-a.maxHeight;if((a=!b.width&&!b.height)&&!b.left&&b.top)b.top=null;else if(a&&!b.top&&b.left)b.left=null;return b},_proportionallyResize:function(){if(this._proportionallyResizeElements.length)for(var b=this.helper||this.element,a=0;a');var a=e.browser.msie&&e.browser.version<7,c=a?1:0;a=a?2:-1;this.helper.addClass(this._helper).css({width:this.element.outerWidth()+a,height:this.element.outerHeight()+a,position:"absolute",left:this.elementOffset.left-c+"px",top:this.elementOffset.top-c+"px",zIndex:++b.zIndex});this.helper.appendTo("body").disableSelection()}else this.helper=this.element},_change:{e:function(b,a){return{width:this.originalSize.width+ +a}},w:function(b,a){return{left:this.originalPosition.left+a,width:this.originalSize.width-a}},n:function(b,a,c){return{top:this.originalPosition.top+c,height:this.originalSize.height-c}},s:function(b,a,c){return{height:this.originalSize.height+c}},se:function(b,a,c){return e.extend(this._change.s.apply(this,arguments),this._change.e.apply(this,[b,a,c]))},sw:function(b,a,c){return e.extend(this._change.s.apply(this,arguments),this._change.w.apply(this,[b,a,c]))},ne:function(b,a,c){return e.extend(this._change.n.apply(this, +arguments),this._change.e.apply(this,[b,a,c]))},nw:function(b,a,c){return e.extend(this._change.n.apply(this,arguments),this._change.w.apply(this,[b,a,c]))}},_propagate:function(b,a){e.ui.plugin.call(this,b,[a,this.ui()]);b!="resize"&&this._trigger(b,a,this.ui())},plugins:{},ui:function(){return{originalElement:this.originalElement,element:this.element,helper:this.helper,position:this.position,size:this.size,originalSize:this.originalSize,originalPosition:this.originalPosition}}});e.extend(e.ui.resizable, +{version:"1.8.7"});e.ui.plugin.add("resizable","alsoResize",{start:function(){var b=e(this).data("resizable").options,a=function(c){e(c).each(function(){var d=e(this);d.data("resizable-alsoresize",{width:parseInt(d.width(),10),height:parseInt(d.height(),10),left:parseInt(d.css("left"),10),top:parseInt(d.css("top"),10),position:d.css("position")})})};if(typeof b.alsoResize=="object"&&!b.alsoResize.parentNode)if(b.alsoResize.length){b.alsoResize=b.alsoResize[0];a(b.alsoResize)}else e.each(b.alsoResize, +function(c){a(c)});else a(b.alsoResize)},resize:function(b,a){var c=e(this).data("resizable");b=c.options;var d=c.originalSize,f=c.originalPosition,g={height:c.size.height-d.height||0,width:c.size.width-d.width||0,top:c.position.top-f.top||0,left:c.position.left-f.left||0},h=function(i,j){e(i).each(function(){var k=e(this),q=e(this).data("resizable-alsoresize"),p={},r=j&&j.length?j:k.parents(a.originalElement[0]).length?["width","height"]:["width","height","top","left"];e.each(r,function(n,o){if((n= +(q[o]||0)+(g[o]||0))&&n>=0)p[o]=n||null});if(e.browser.opera&&/relative/.test(k.css("position"))){c._revertToRelativePosition=true;k.css({position:"absolute",top:"auto",left:"auto"})}k.css(p)})};typeof b.alsoResize=="object"&&!b.alsoResize.nodeType?e.each(b.alsoResize,function(i,j){h(i,j)}):h(b.alsoResize)},stop:function(){var b=e(this).data("resizable"),a=b.options,c=function(d){e(d).each(function(){var f=e(this);f.css({position:f.data("resizable-alsoresize").position})})};if(b._revertToRelativePosition){b._revertToRelativePosition= +false;typeof a.alsoResize=="object"&&!a.alsoResize.nodeType?e.each(a.alsoResize,function(d){c(d)}):c(a.alsoResize)}e(this).removeData("resizable-alsoresize")}});e.ui.plugin.add("resizable","animate",{stop:function(b){var a=e(this).data("resizable"),c=a.options,d=a._proportionallyResizeElements,f=d.length&&/textarea/i.test(d[0].nodeName),g=f&&e.ui.hasScroll(d[0],"left")?0:a.sizeDiff.height;f={width:a.size.width-(f?0:a.sizeDiff.width),height:a.size.height-g};g=parseInt(a.element.css("left"),10)+(a.position.left- +a.originalPosition.left)||null;var h=parseInt(a.element.css("top"),10)+(a.position.top-a.originalPosition.top)||null;a.element.animate(e.extend(f,h&&g?{top:h,left:g}:{}),{duration:c.animateDuration,easing:c.animateEasing,step:function(){var i={width:parseInt(a.element.css("width"),10),height:parseInt(a.element.css("height"),10),top:parseInt(a.element.css("top"),10),left:parseInt(a.element.css("left"),10)};d&&d.length&&e(d[0]).css({width:i.width,height:i.height});a._updateCache(i);a._propagate("resize", +b)}})}});e.ui.plugin.add("resizable","containment",{start:function(){var b=e(this).data("resizable"),a=b.element,c=b.options.containment;if(a=c instanceof e?c.get(0):/parent/.test(c)?a.parent().get(0):c){b.containerElement=e(a);if(/document/.test(c)||c==document){b.containerOffset={left:0,top:0};b.containerPosition={left:0,top:0};b.parentData={element:e(document),left:0,top:0,width:e(document).width(),height:e(document).height()||document.body.parentNode.scrollHeight}}else{var d=e(a),f=[];e(["Top", +"Right","Left","Bottom"]).each(function(i,j){f[i]=m(d.css("padding"+j))});b.containerOffset=d.offset();b.containerPosition=d.position();b.containerSize={height:d.innerHeight()-f[3],width:d.innerWidth()-f[1]};c=b.containerOffset;var g=b.containerSize.height,h=b.containerSize.width;h=e.ui.hasScroll(a,"left")?a.scrollWidth:h;g=e.ui.hasScroll(a)?a.scrollHeight:g;b.parentData={element:a,left:c.left,top:c.top,width:h,height:g}}}},resize:function(b){var a=e(this).data("resizable"),c=a.options,d=a.containerOffset, +f=a.position;b=a._aspectRatio||b.shiftKey;var g={top:0,left:0},h=a.containerElement;if(h[0]!=document&&/static/.test(h.css("position")))g=d;if(f.left<(a._helper?d.left:0)){a.size.width+=a._helper?a.position.left-d.left:a.position.left-g.left;if(b)a.size.height=a.size.width/c.aspectRatio;a.position.left=c.helper?d.left:0}if(f.top<(a._helper?d.top:0)){a.size.height+=a._helper?a.position.top-d.top:a.position.top;if(b)a.size.width=a.size.height*c.aspectRatio;a.position.top=a._helper?d.top:0}a.offset.left= +a.parentData.left+a.position.left;a.offset.top=a.parentData.top+a.position.top;c=Math.abs((a._helper?a.offset.left-g.left:a.offset.left-g.left)+a.sizeDiff.width);d=Math.abs((a._helper?a.offset.top-g.top:a.offset.top-d.top)+a.sizeDiff.height);f=a.containerElement.get(0)==a.element.parent().get(0);g=/relative|absolute/.test(a.containerElement.css("position"));if(f&&g)c-=a.parentData.left;if(c+a.size.width>=a.parentData.width){a.size.width=a.parentData.width-c;if(b)a.size.height=a.size.width/a.aspectRatio}if(d+ +a.size.height>=a.parentData.height){a.size.height=a.parentData.height-d;if(b)a.size.width=a.size.height*a.aspectRatio}},stop:function(){var b=e(this).data("resizable"),a=b.options,c=b.containerOffset,d=b.containerPosition,f=b.containerElement,g=e(b.helper),h=g.offset(),i=g.outerWidth()-b.sizeDiff.width;g=g.outerHeight()-b.sizeDiff.height;b._helper&&!a.animate&&/relative/.test(f.css("position"))&&e(this).css({left:h.left-d.left-c.left,width:i,height:g});b._helper&&!a.animate&&/static/.test(f.css("position"))&& +e(this).css({left:h.left-d.left-c.left,width:i,height:g})}});e.ui.plugin.add("resizable","ghost",{start:function(){var b=e(this).data("resizable"),a=b.options,c=b.size;b.ghost=b.originalElement.clone();b.ghost.css({opacity:0.25,display:"block",position:"relative",height:c.height,width:c.width,margin:0,left:0,top:0}).addClass("ui-resizable-ghost").addClass(typeof a.ghost=="string"?a.ghost:"");b.ghost.appendTo(b.helper)},resize:function(){var b=e(this).data("resizable");b.ghost&&b.ghost.css({position:"relative", +height:b.size.height,width:b.size.width})},stop:function(){var b=e(this).data("resizable");b.ghost&&b.helper&&b.helper.get(0).removeChild(b.ghost.get(0))}});e.ui.plugin.add("resizable","grid",{resize:function(){var b=e(this).data("resizable"),a=b.options,c=b.size,d=b.originalSize,f=b.originalPosition,g=b.axis;a.grid=typeof a.grid=="number"?[a.grid,a.grid]:a.grid;var h=Math.round((c.width-d.width)/(a.grid[0]||1))*(a.grid[0]||1);a=Math.round((c.height-d.height)/(a.grid[1]||1))*(a.grid[1]||1);if(/^(se|s|e)$/.test(g)){b.size.width= +d.width+h;b.size.height=d.height+a}else if(/^(ne)$/.test(g)){b.size.width=d.width+h;b.size.height=d.height+a;b.position.top=f.top-a}else{if(/^(sw)$/.test(g)){b.size.width=d.width+h;b.size.height=d.height+a}else{b.size.width=d.width+h;b.size.height=d.height+a;b.position.top=f.top-a}b.position.left=f.left-h}}});var m=function(b){return parseInt(b,10)||0},l=function(b){return!isNaN(parseInt(b,10))}})(jQuery); +;/* + * jQuery UI Selectable 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Selectables + * + * Depends: + * jquery.ui.core.js + * jquery.ui.mouse.js + * jquery.ui.widget.js + */ +(function(e){e.widget("ui.selectable",e.ui.mouse,{options:{appendTo:"body",autoRefresh:true,distance:0,filter:"*",tolerance:"touch"},_create:function(){var c=this;this.element.addClass("ui-selectable");this.dragged=false;var f;this.refresh=function(){f=e(c.options.filter,c.element[0]);f.each(function(){var d=e(this),b=d.offset();e.data(this,"selectable-item",{element:this,$element:d,left:b.left,top:b.top,right:b.left+d.outerWidth(),bottom:b.top+d.outerHeight(),startselected:false,selected:d.hasClass("ui-selected"), +selecting:d.hasClass("ui-selecting"),unselecting:d.hasClass("ui-unselecting")})})};this.refresh();this.selectees=f.addClass("ui-selectee");this._mouseInit();this.helper=e("
")},destroy:function(){this.selectees.removeClass("ui-selectee").removeData("selectable-item");this.element.removeClass("ui-selectable ui-selectable-disabled").removeData("selectable").unbind(".selectable");this._mouseDestroy();return this},_mouseStart:function(c){var f=this;this.opos=[c.pageX, +c.pageY];if(!this.options.disabled){var d=this.options;this.selectees=e(d.filter,this.element[0]);this._trigger("start",c);e(d.appendTo).append(this.helper);this.helper.css({left:c.clientX,top:c.clientY,width:0,height:0});d.autoRefresh&&this.refresh();this.selectees.filter(".ui-selected").each(function(){var b=e.data(this,"selectable-item");b.startselected=true;if(!c.metaKey){b.$element.removeClass("ui-selected");b.selected=false;b.$element.addClass("ui-unselecting");b.unselecting=true;f._trigger("unselecting", +c,{unselecting:b.element})}});e(c.target).parents().andSelf().each(function(){var b=e.data(this,"selectable-item");if(b){var g=!c.metaKey||!b.$element.hasClass("ui-selected");b.$element.removeClass(g?"ui-unselecting":"ui-selected").addClass(g?"ui-selecting":"ui-unselecting");b.unselecting=!g;b.selecting=g;(b.selected=g)?f._trigger("selecting",c,{selecting:b.element}):f._trigger("unselecting",c,{unselecting:b.element});return false}})}},_mouseDrag:function(c){var f=this;this.dragged=true;if(!this.options.disabled){var d= +this.options,b=this.opos[0],g=this.opos[1],h=c.pageX,i=c.pageY;if(b>h){var j=h;h=b;b=j}if(g>i){j=i;i=g;g=j}this.helper.css({left:b,top:g,width:h-b,height:i-g});this.selectees.each(function(){var a=e.data(this,"selectable-item");if(!(!a||a.element==f.element[0])){var k=false;if(d.tolerance=="touch")k=!(a.left>h||a.righti||a.bottomb&&a.rightg&&a.bottom *",opacity:false,placeholder:false,revert:false,scroll:true,scrollSensitivity:20,scrollSpeed:20,scope:"default",tolerance:"intersect",zIndex:1E3},_create:function(){this.containerCache={};this.element.addClass("ui-sortable"); +this.refresh();this.floating=this.items.length?/left|right/.test(this.items[0].item.css("float")):false;this.offset=this.element.offset();this._mouseInit()},destroy:function(){this.element.removeClass("ui-sortable ui-sortable-disabled").removeData("sortable").unbind(".sortable");this._mouseDestroy();for(var a=this.items.length-1;a>=0;a--)this.items[a].item.removeData("sortable-item");return this},_setOption:function(a,b){if(a==="disabled"){this.options[a]=b;this.widget()[b?"addClass":"removeClass"]("ui-sortable-disabled")}else d.Widget.prototype._setOption.apply(this, +arguments)},_mouseCapture:function(a,b){if(this.reverting)return false;if(this.options.disabled||this.options.type=="static")return false;this._refreshItems(a);var c=null,e=this;d(a.target).parents().each(function(){if(d.data(this,"sortable-item")==e){c=d(this);return false}});if(d.data(a.target,"sortable-item")==e)c=d(a.target);if(!c)return false;if(this.options.handle&&!b){var f=false;d(this.options.handle,c).find("*").andSelf().each(function(){if(this==a.target)f=true});if(!f)return false}this.currentItem= +c;this._removeCurrentsFromItems();return true},_mouseStart:function(a,b,c){b=this.options;var e=this;this.currentContainer=this;this.refreshPositions();this.helper=this._createHelper(a);this._cacheHelperProportions();this._cacheMargins();this.scrollParent=this.helper.scrollParent();this.offset=this.currentItem.offset();this.offset={top:this.offset.top-this.margins.top,left:this.offset.left-this.margins.left};this.helper.css("position","absolute");this.cssPosition=this.helper.css("position");d.extend(this.offset, +{click:{left:a.pageX-this.offset.left,top:a.pageY-this.offset.top},parent:this._getParentOffset(),relative:this._getRelativeOffset()});this.originalPosition=this._generatePosition(a);this.originalPageX=a.pageX;this.originalPageY=a.pageY;b.cursorAt&&this._adjustOffsetFromHelper(b.cursorAt);this.domPosition={prev:this.currentItem.prev()[0],parent:this.currentItem.parent()[0]};this.helper[0]!=this.currentItem[0]&&this.currentItem.hide();this._createPlaceholder();b.containment&&this._setContainment(); +if(b.cursor){if(d("body").css("cursor"))this._storedCursor=d("body").css("cursor");d("body").css("cursor",b.cursor)}if(b.opacity){if(this.helper.css("opacity"))this._storedOpacity=this.helper.css("opacity");this.helper.css("opacity",b.opacity)}if(b.zIndex){if(this.helper.css("zIndex"))this._storedZIndex=this.helper.css("zIndex");this.helper.css("zIndex",b.zIndex)}if(this.scrollParent[0]!=document&&this.scrollParent[0].tagName!="HTML")this.overflowOffset=this.scrollParent.offset();this._trigger("start", +a,this._uiHash());this._preserveHelperProportions||this._cacheHelperProportions();if(!c)for(c=this.containers.length-1;c>=0;c--)this.containers[c]._trigger("activate",a,e._uiHash(this));if(d.ui.ddmanager)d.ui.ddmanager.current=this;d.ui.ddmanager&&!b.dropBehaviour&&d.ui.ddmanager.prepareOffsets(this,a);this.dragging=true;this.helper.addClass("ui-sortable-helper");this._mouseDrag(a);return true},_mouseDrag:function(a){this.position=this._generatePosition(a);this.positionAbs=this._convertPositionTo("absolute"); +if(!this.lastPositionAbs)this.lastPositionAbs=this.positionAbs;if(this.options.scroll){var b=this.options,c=false;if(this.scrollParent[0]!=document&&this.scrollParent[0].tagName!="HTML"){if(this.overflowOffset.top+this.scrollParent[0].offsetHeight-a.pageY=0;b--){c=this.items[b];var e=c.item[0],f=this._intersectsWithPointer(c);if(f)if(e!=this.currentItem[0]&&this.placeholder[f==1?"next":"prev"]()[0]!=e&&!d.ui.contains(this.placeholder[0],e)&&(this.options.type=="semi-dynamic"?!d.ui.contains(this.element[0],e):true)){this.direction=f==1?"down":"up";if(this.options.tolerance=="pointer"||this._intersectsWithSides(c))this._rearrange(a, +c);else break;this._trigger("change",a,this._uiHash());break}}this._contactContainers(a);d.ui.ddmanager&&d.ui.ddmanager.drag(this,a);this._trigger("sort",a,this._uiHash());this.lastPositionAbs=this.positionAbs;return false},_mouseStop:function(a,b){if(a){d.ui.ddmanager&&!this.options.dropBehaviour&&d.ui.ddmanager.drop(this,a);if(this.options.revert){var c=this;b=c.placeholder.offset();c.reverting=true;d(this.helper).animate({left:b.left-this.offset.parent.left-c.margins.left+(this.offsetParent[0]== +document.body?0:this.offsetParent[0].scrollLeft),top:b.top-this.offset.parent.top-c.margins.top+(this.offsetParent[0]==document.body?0:this.offsetParent[0].scrollTop)},parseInt(this.options.revert,10)||500,function(){c._clear(a)})}else this._clear(a,b);return false}},cancel:function(){var a=this;if(this.dragging){this._mouseUp();this.options.helper=="original"?this.currentItem.css(this._storedCSS).removeClass("ui-sortable-helper"):this.currentItem.show();for(var b=this.containers.length-1;b>=0;b--){this.containers[b]._trigger("deactivate", +null,a._uiHash(this));if(this.containers[b].containerCache.over){this.containers[b]._trigger("out",null,a._uiHash(this));this.containers[b].containerCache.over=0}}}this.placeholder[0].parentNode&&this.placeholder[0].parentNode.removeChild(this.placeholder[0]);this.options.helper!="original"&&this.helper&&this.helper[0].parentNode&&this.helper.remove();d.extend(this,{helper:null,dragging:false,reverting:false,_noFinalSort:null});this.domPosition.prev?d(this.domPosition.prev).after(this.currentItem): +d(this.domPosition.parent).prepend(this.currentItem);return this},serialize:function(a){var b=this._getItemsAsjQuery(a&&a.connected),c=[];a=a||{};d(b).each(function(){var e=(d(a.item||this).attr(a.attribute||"id")||"").match(a.expression||/(.+)[-=_](.+)/);if(e)c.push((a.key||e[1]+"[]")+"="+(a.key&&a.expression?e[1]:e[2]))});!c.length&&a.key&&c.push(a.key+"=");return c.join("&")},toArray:function(a){var b=this._getItemsAsjQuery(a&&a.connected),c=[];a=a||{};b.each(function(){c.push(d(a.item||this).attr(a.attribute|| +"id")||"")});return c},_intersectsWith:function(a){var b=this.positionAbs.left,c=b+this.helperProportions.width,e=this.positionAbs.top,f=e+this.helperProportions.height,g=a.left,h=g+a.width,i=a.top,k=i+a.height,j=this.offset.click.top,l=this.offset.click.left;j=e+j>i&&e+jg&&b+la[this.floating?"width":"height"]?j:g0?"down":"up")}, +_getDragHorizontalDirection:function(){var a=this.positionAbs.left-this.lastPositionAbs.left;return a!=0&&(a>0?"right":"left")},refresh:function(a){this._refreshItems(a);this.refreshPositions();return this},_connectWith:function(){var a=this.options;return a.connectWith.constructor==String?[a.connectWith]:a.connectWith},_getItemsAsjQuery:function(a){var b=[],c=[],e=this._connectWith();if(e&&a)for(a=e.length-1;a>=0;a--)for(var f=d(e[a]),g=f.length-1;g>=0;g--){var h=d.data(f[g],"sortable");if(h&&h!= +this&&!h.options.disabled)c.push([d.isFunction(h.options.items)?h.options.items.call(h.element):d(h.options.items,h.element).not(".ui-sortable-helper").not(".ui-sortable-placeholder"),h])}c.push([d.isFunction(this.options.items)?this.options.items.call(this.element,null,{options:this.options,item:this.currentItem}):d(this.options.items,this.element).not(".ui-sortable-helper").not(".ui-sortable-placeholder"),this]);for(a=c.length-1;a>=0;a--)c[a][0].each(function(){b.push(this)});return d(b)},_removeCurrentsFromItems:function(){for(var a= +this.currentItem.find(":data(sortable-item)"),b=0;b=0;f--)for(var g=d(e[f]),h=g.length-1;h>=0;h--){var i=d.data(g[h],"sortable"); +if(i&&i!=this&&!i.options.disabled){c.push([d.isFunction(i.options.items)?i.options.items.call(i.element[0],a,{item:this.currentItem}):d(i.options.items,i.element),i]);this.containers.push(i)}}for(f=c.length-1;f>=0;f--){a=c[f][1];e=c[f][0];h=0;for(g=e.length;h= +0;b--){var c=this.items[b],e=this.options.toleranceElement?d(this.options.toleranceElement,c.item):c.item;if(!a){c.width=e.outerWidth();c.height=e.outerHeight()}e=e.offset();c.left=e.left;c.top=e.top}if(this.options.custom&&this.options.custom.refreshContainers)this.options.custom.refreshContainers.call(this);else for(b=this.containers.length-1;b>=0;b--){e=this.containers[b].element.offset();this.containers[b].containerCache.left=e.left;this.containers[b].containerCache.top=e.top;this.containers[b].containerCache.width= +this.containers[b].element.outerWidth();this.containers[b].containerCache.height=this.containers[b].element.outerHeight()}return this},_createPlaceholder:function(a){var b=a||this,c=b.options;if(!c.placeholder||c.placeholder.constructor==String){var e=c.placeholder;c.placeholder={element:function(){var f=d(document.createElement(b.currentItem[0].nodeName)).addClass(e||b.currentItem[0].className+" ui-sortable-placeholder").removeClass("ui-sortable-helper")[0];if(!e)f.style.visibility="hidden";return f}, +update:function(f,g){if(!(e&&!c.forcePlaceholderSize)){g.height()||g.height(b.currentItem.innerHeight()-parseInt(b.currentItem.css("paddingTop")||0,10)-parseInt(b.currentItem.css("paddingBottom")||0,10));g.width()||g.width(b.currentItem.innerWidth()-parseInt(b.currentItem.css("paddingLeft")||0,10)-parseInt(b.currentItem.css("paddingRight")||0,10))}}}}b.placeholder=d(c.placeholder.element.call(b.element,b.currentItem));b.currentItem.after(b.placeholder);c.placeholder.update(b,b.placeholder)},_contactContainers:function(a){for(var b= +null,c=null,e=this.containers.length-1;e>=0;e--)if(!d.ui.contains(this.currentItem[0],this.containers[e].element[0]))if(this._intersectsWith(this.containers[e].containerCache)){if(!(b&&d.ui.contains(this.containers[e].element[0],b.element[0]))){b=this.containers[e];c=e}}else if(this.containers[e].containerCache.over){this.containers[e]._trigger("out",a,this._uiHash(this));this.containers[e].containerCache.over=0}if(b)if(this.containers.length===1){this.containers[c]._trigger("over",a,this._uiHash(this)); +this.containers[c].containerCache.over=1}else if(this.currentContainer!=this.containers[c]){b=1E4;e=null;for(var f=this.positionAbs[this.containers[c].floating?"left":"top"],g=this.items.length-1;g>=0;g--)if(d.ui.contains(this.containers[c].element[0],this.items[g].item[0])){var h=this.items[g][this.containers[c].floating?"left":"top"];if(Math.abs(h-f)this.containment[2])f=this.containment[2]+this.offset.click.left;if(a.pageY-this.offset.click.top>this.containment[3])g=this.containment[3]+this.offset.click.top}if(b.grid){g=this.originalPageY+Math.round((g-this.originalPageY)/b.grid[1])*b.grid[1];g=this.containment?!(g-this.offset.click.topthis.containment[3])? +g:!(g-this.offset.click.topthis.containment[2])?f:!(f-this.offset.click.left=0;e--)if(d.ui.contains(this.containers[e].element[0],this.currentItem[0])&&!b){c.push(function(f){return function(g){f._trigger("receive", +g,this._uiHash(this))}}.call(this,this.containers[e]));c.push(function(f){return function(g){f._trigger("update",g,this._uiHash(this))}}.call(this,this.containers[e]))}}for(e=this.containers.length-1;e>=0;e--){b||c.push(function(f){return function(g){f._trigger("deactivate",g,this._uiHash(this))}}.call(this,this.containers[e]));if(this.containers[e].containerCache.over){c.push(function(f){return function(g){f._trigger("out",g,this._uiHash(this))}}.call(this,this.containers[e]));this.containers[e].containerCache.over= +0}}this._storedCursor&&d("body").css("cursor",this._storedCursor);this._storedOpacity&&this.helper.css("opacity",this._storedOpacity);if(this._storedZIndex)this.helper.css("zIndex",this._storedZIndex=="auto"?"":this._storedZIndex);this.dragging=false;if(this.cancelHelperRemoval){if(!b){this._trigger("beforeStop",a,this._uiHash());for(e=0;e li > :first-child,> :not(li):even",icons:{header:"ui-icon-triangle-1-e",headerSelected:"ui-icon-triangle-1-s"},navigation:false,navigationFilter:function(){return this.href.toLowerCase()===location.href.toLowerCase()}},_create:function(){var a=this,b=a.options;a.running=0;a.element.addClass("ui-accordion ui-widget ui-helper-reset").children("li").addClass("ui-accordion-li-fix"); +a.headers=a.element.find(b.header).addClass("ui-accordion-header ui-helper-reset ui-state-default ui-corner-all").bind("mouseenter.accordion",function(){b.disabled||c(this).addClass("ui-state-hover")}).bind("mouseleave.accordion",function(){b.disabled||c(this).removeClass("ui-state-hover")}).bind("focus.accordion",function(){b.disabled||c(this).addClass("ui-state-focus")}).bind("blur.accordion",function(){b.disabled||c(this).removeClass("ui-state-focus")});a.headers.next().addClass("ui-accordion-content ui-helper-reset ui-widget-content ui-corner-bottom"); +if(b.navigation){var d=a.element.find("a").filter(b.navigationFilter).eq(0);if(d.length){var f=d.closest(".ui-accordion-header");a.active=f.length?f:d.closest(".ui-accordion-content").prev()}}a.active=a._findActive(a.active||b.active).addClass("ui-state-default ui-state-active").toggleClass("ui-corner-all").toggleClass("ui-corner-top");a.active.next().addClass("ui-accordion-content-active");a._createIcons();a.resize();a.element.attr("role","tablist");a.headers.attr("role","tab").bind("keydown.accordion", +function(g){return a._keydown(g)}).next().attr("role","tabpanel");a.headers.not(a.active||"").attr({"aria-expanded":"false",tabIndex:-1}).next().hide();a.active.length?a.active.attr({"aria-expanded":"true",tabIndex:0}):a.headers.eq(0).attr("tabIndex",0);c.browser.safari||a.headers.find("a").attr("tabIndex",-1);b.event&&a.headers.bind(b.event.split(" ").join(".accordion ")+".accordion",function(g){a._clickHandler.call(a,g,this);g.preventDefault()})},_createIcons:function(){var a=this.options;if(a.icons){c("").addClass("ui-icon "+ +a.icons.header).prependTo(this.headers);this.active.children(".ui-icon").toggleClass(a.icons.header).toggleClass(a.icons.headerSelected);this.element.addClass("ui-accordion-icons")}},_destroyIcons:function(){this.headers.children(".ui-icon").remove();this.element.removeClass("ui-accordion-icons")},destroy:function(){var a=this.options;this.element.removeClass("ui-accordion ui-widget ui-helper-reset").removeAttr("role");this.headers.unbind(".accordion").removeClass("ui-accordion-header ui-accordion-disabled ui-helper-reset ui-state-default ui-corner-all ui-state-active ui-state-disabled ui-corner-top").removeAttr("role").removeAttr("aria-expanded").removeAttr("tabIndex"); +this.headers.find("a").removeAttr("tabIndex");this._destroyIcons();var b=this.headers.next().css("display","").removeAttr("role").removeClass("ui-helper-reset ui-widget-content ui-corner-bottom ui-accordion-content ui-accordion-content-active ui-accordion-disabled ui-state-disabled");if(a.autoHeight||a.fillHeight)b.css("height","");return c.Widget.prototype.destroy.call(this)},_setOption:function(a,b){c.Widget.prototype._setOption.apply(this,arguments);a=="active"&&this.activate(b);if(a=="icons"){this._destroyIcons(); +b&&this._createIcons()}if(a=="disabled")this.headers.add(this.headers.next())[b?"addClass":"removeClass"]("ui-accordion-disabled ui-state-disabled")},_keydown:function(a){if(!(this.options.disabled||a.altKey||a.ctrlKey)){var b=c.ui.keyCode,d=this.headers.length,f=this.headers.index(a.target),g=false;switch(a.keyCode){case b.RIGHT:case b.DOWN:g=this.headers[(f+1)%d];break;case b.LEFT:case b.UP:g=this.headers[(f-1+d)%d];break;case b.SPACE:case b.ENTER:this._clickHandler({target:a.target},a.target); +a.preventDefault()}if(g){c(a.target).attr("tabIndex",-1);c(g).attr("tabIndex",0);g.focus();return false}return true}},resize:function(){var a=this.options,b;if(a.fillSpace){if(c.browser.msie){var d=this.element.parent().css("overflow");this.element.parent().css("overflow","hidden")}b=this.element.parent().height();c.browser.msie&&this.element.parent().css("overflow",d);this.headers.each(function(){b-=c(this).outerHeight(true)});this.headers.next().each(function(){c(this).height(Math.max(0,b-c(this).innerHeight()+ +c(this).height()))}).css("overflow","auto")}else if(a.autoHeight){b=0;this.headers.next().each(function(){b=Math.max(b,c(this).height("").height())}).height(b)}return this},activate:function(a){this.options.active=a;a=this._findActive(a)[0];this._clickHandler({target:a},a);return this},_findActive:function(a){return a?typeof a==="number"?this.headers.filter(":eq("+a+")"):this.headers.not(this.headers.not(a)):a===false?c([]):this.headers.filter(":eq(0)")},_clickHandler:function(a,b){var d=this.options; +if(!d.disabled)if(a.target){a=c(a.currentTarget||b);b=a[0]===this.active[0];d.active=d.collapsible&&b?false:this.headers.index(a);if(!(this.running||!d.collapsible&&b)){this.active.removeClass("ui-state-active ui-corner-top").addClass("ui-state-default ui-corner-all").children(".ui-icon").removeClass(d.icons.headerSelected).addClass(d.icons.header);if(!b){a.removeClass("ui-state-default ui-corner-all").addClass("ui-state-active ui-corner-top").children(".ui-icon").removeClass(d.icons.header).addClass(d.icons.headerSelected); +a.next().addClass("ui-accordion-content-active")}h=a.next();f=this.active.next();g={options:d,newHeader:b&&d.collapsible?c([]):a,oldHeader:this.active,newContent:b&&d.collapsible?c([]):h,oldContent:f};d=this.headers.index(this.active[0])>this.headers.index(a[0]);this.active=b?c([]):a;this._toggle(h,f,g,b,d)}}else if(d.collapsible){this.active.removeClass("ui-state-active ui-corner-top").addClass("ui-state-default ui-corner-all").children(".ui-icon").removeClass(d.icons.headerSelected).addClass(d.icons.header); +this.active.next().addClass("ui-accordion-content-active");var f=this.active.next(),g={options:d,newHeader:c([]),oldHeader:d.active,newContent:c([]),oldContent:f},h=this.active=c([]);this._toggle(h,f,g)}},_toggle:function(a,b,d,f,g){var h=this,e=h.options;h.toShow=a;h.toHide=b;h.data=d;var j=function(){if(h)return h._completed.apply(h,arguments)};h._trigger("changestart",null,h.data);h.running=b.size()===0?a.size():b.size();if(e.animated){d={};d=e.collapsible&&f?{toShow:c([]),toHide:b,complete:j, +down:g,autoHeight:e.autoHeight||e.fillSpace}:{toShow:a,toHide:b,complete:j,down:g,autoHeight:e.autoHeight||e.fillSpace};if(!e.proxied)e.proxied=e.animated;if(!e.proxiedDuration)e.proxiedDuration=e.duration;e.animated=c.isFunction(e.proxied)?e.proxied(d):e.proxied;e.duration=c.isFunction(e.proxiedDuration)?e.proxiedDuration(d):e.proxiedDuration;f=c.ui.accordion.animations;var i=e.duration,k=e.animated;if(k&&!f[k]&&!c.easing[k])k="slide";f[k]||(f[k]=function(l){this.slide(l,{easing:k,duration:i||700})}); +f[k](d)}else{if(e.collapsible&&f)a.toggle();else{b.hide();a.show()}j(true)}b.prev().attr({"aria-expanded":"false",tabIndex:-1}).blur();a.prev().attr({"aria-expanded":"true",tabIndex:0}).focus()},_completed:function(a){this.running=a?0:--this.running;if(!this.running){this.options.clearStyle&&this.toShow.add(this.toHide).css({height:"",overflow:""});this.toHide.removeClass("ui-accordion-content-active");this._trigger("change",null,this.data)}}});c.extend(c.ui.accordion,{version:"1.8.7",animations:{slide:function(a, +b){a=c.extend({easing:"swing",duration:300},a,b);if(a.toHide.size())if(a.toShow.size()){var d=a.toShow.css("overflow"),f=0,g={},h={},e;b=a.toShow;e=b[0].style.width;b.width(parseInt(b.parent().width(),10)-parseInt(b.css("paddingLeft"),10)-parseInt(b.css("paddingRight"),10)-(parseInt(b.css("borderLeftWidth"),10)||0)-(parseInt(b.css("borderRightWidth"),10)||0));c.each(["height","paddingTop","paddingBottom"],function(j,i){h[i]="hide";j=(""+c.css(a.toShow[0],i)).match(/^([\d+-.]+)(.*)$/);g[i]={value:j[1], +unit:j[2]||"px"}});a.toShow.css({height:0,overflow:"hidden"}).show();a.toHide.filter(":hidden").each(a.complete).end().filter(":visible").animate(h,{step:function(j,i){if(i.prop=="height")f=i.end-i.start===0?0:(i.now-i.start)/(i.end-i.start);a.toShow[0].style[i.prop]=f*g[i.prop].value+g[i.prop].unit},duration:a.duration,easing:a.easing,complete:function(){a.autoHeight||a.toShow.css("height","");a.toShow.css({width:e,overflow:d});a.complete()}})}else a.toHide.animate({height:"hide",paddingTop:"hide", +paddingBottom:"hide"},a);else a.toShow.animate({height:"show",paddingTop:"show",paddingBottom:"show"},a)},bounceslide:function(a){this.slide(a,{easing:a.down?"easeOutBounce":"swing",duration:a.down?1E3:200})}}})})(jQuery); +;/* + * jQuery UI Autocomplete 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Autocomplete + * + * Depends: + * jquery.ui.core.js + * jquery.ui.widget.js + * jquery.ui.position.js + */ +(function(d){d.widget("ui.autocomplete",{options:{appendTo:"body",delay:300,minLength:1,position:{my:"left top",at:"left bottom",collision:"none"},source:null},_create:function(){var a=this,b=this.element[0].ownerDocument,f;this.element.addClass("ui-autocomplete-input").attr("autocomplete","off").attr({role:"textbox","aria-autocomplete":"list","aria-haspopup":"true"}).bind("keydown.autocomplete",function(c){if(!(a.options.disabled||a.element.attr("readonly"))){f=false;var e=d.ui.keyCode;switch(c.keyCode){case e.PAGE_UP:a._move("previousPage", +c);break;case e.PAGE_DOWN:a._move("nextPage",c);break;case e.UP:a._move("previous",c);c.preventDefault();break;case e.DOWN:a._move("next",c);c.preventDefault();break;case e.ENTER:case e.NUMPAD_ENTER:if(a.menu.active){f=true;c.preventDefault()}case e.TAB:if(!a.menu.active)return;a.menu.select(c);break;case e.ESCAPE:a.element.val(a.term);a.close(c);break;default:clearTimeout(a.searching);a.searching=setTimeout(function(){if(a.term!=a.element.val()){a.selectedItem=null;a.search(null,c)}},a.options.delay); +break}}}).bind("keypress.autocomplete",function(c){if(f){f=false;c.preventDefault()}}).bind("focus.autocomplete",function(){if(!a.options.disabled){a.selectedItem=null;a.previous=a.element.val()}}).bind("blur.autocomplete",function(c){if(!a.options.disabled){clearTimeout(a.searching);a.closing=setTimeout(function(){a.close(c);a._change(c)},150)}});this._initSource();this.response=function(){return a._response.apply(a,arguments)};this.menu=d("
    ").addClass("ui-autocomplete").appendTo(d(this.options.appendTo|| +"body",b)[0]).mousedown(function(c){var e=a.menu.element[0];d(c.target).closest(".ui-menu-item").length||setTimeout(function(){d(document).one("mousedown",function(g){g.target!==a.element[0]&&g.target!==e&&!d.ui.contains(e,g.target)&&a.close()})},1);setTimeout(function(){clearTimeout(a.closing)},13)}).menu({focus:function(c,e){e=e.item.data("item.autocomplete");false!==a._trigger("focus",c,{item:e})&&/^key/.test(c.originalEvent.type)&&a.element.val(e.value)},selected:function(c,e){var g=e.item.data("item.autocomplete"), +h=a.previous;if(a.element[0]!==b.activeElement){a.element.focus();a.previous=h;setTimeout(function(){a.previous=h;a.selectedItem=g},1)}false!==a._trigger("select",c,{item:g})&&a.element.val(g.value);a.term=a.element.val();a.close(c);a.selectedItem=g},blur:function(){a.menu.element.is(":visible")&&a.element.val()!==a.term&&a.element.val(a.term)}}).zIndex(this.element.zIndex()+1).css({top:0,left:0}).hide().data("menu");d.fn.bgiframe&&this.menu.element.bgiframe()},destroy:function(){this.element.removeClass("ui-autocomplete-input").removeAttr("autocomplete").removeAttr("role").removeAttr("aria-autocomplete").removeAttr("aria-haspopup"); +this.menu.element.remove();d.Widget.prototype.destroy.call(this)},_setOption:function(a,b){d.Widget.prototype._setOption.apply(this,arguments);a==="source"&&this._initSource();if(a==="appendTo")this.menu.element.appendTo(d(b||"body",this.element[0].ownerDocument)[0])},_initSource:function(){var a=this,b,f;if(d.isArray(this.options.source)){b=this.options.source;this.source=function(c,e){e(d.ui.autocomplete.filter(b,c.term))}}else if(typeof this.options.source==="string"){f=this.options.source;this.source= +function(c,e){a.xhr&&a.xhr.abort();a.xhr=d.ajax({url:f,data:c,dataType:"json",success:function(g,h,i){i===a.xhr&&e(g);a.xhr=null},error:function(g){g===a.xhr&&e([]);a.xhr=null}})}}else this.source=this.options.source},search:function(a,b){a=a!=null?a:this.element.val();this.term=this.element.val();if(a.length").data("item.autocomplete",b).append(d("").text(b.label)).appendTo(a)},_move:function(a,b){if(this.menu.element.is(":visible"))if(this.menu.first()&&/^previous/.test(a)||this.menu.last()&&/^next/.test(a)){this.element.val(this.term);this.menu.deactivate()}else this.menu[a](b);else this.search(null,b)},widget:function(){return this.menu.element}}); +d.extend(d.ui.autocomplete,{escapeRegex:function(a){return a.replace(/[-[\]{}()*+?.,\\^$|#\s]/g,"\\$&")},filter:function(a,b){var f=new RegExp(d.ui.autocomplete.escapeRegex(b),"i");return d.grep(a,function(c){return f.test(c.label||c.value||c)})}})})(jQuery); +(function(d){d.widget("ui.menu",{_create:function(){var a=this;this.element.addClass("ui-menu ui-widget ui-widget-content ui-corner-all").attr({role:"listbox","aria-activedescendant":"ui-active-menuitem"}).click(function(b){if(d(b.target).closest(".ui-menu-item a").length){b.preventDefault();a.select(b)}});this.refresh()},refresh:function(){var a=this;this.element.children("li:not(.ui-menu-item):has(a)").addClass("ui-menu-item").attr("role","menuitem").children("a").addClass("ui-corner-all").attr("tabindex", +-1).mouseenter(function(b){a.activate(b,d(this).parent())}).mouseleave(function(){a.deactivate()})},activate:function(a,b){this.deactivate();if(this.hasScroll()){var f=b.offset().top-this.element.offset().top,c=this.element.attr("scrollTop"),e=this.element.height();if(f<0)this.element.attr("scrollTop",c+f);else f>=e&&this.element.attr("scrollTop",c+f-e+b.height())}this.active=b.eq(0).children("a").addClass("ui-state-hover").attr("id","ui-active-menuitem").end();this._trigger("focus",a,{item:b})}, +deactivate:function(){if(this.active){this.active.children("a").removeClass("ui-state-hover").removeAttr("id");this._trigger("blur");this.active=null}},next:function(a){this.move("next",".ui-menu-item:first",a)},previous:function(a){this.move("prev",".ui-menu-item:last",a)},first:function(){return this.active&&!this.active.prevAll(".ui-menu-item").length},last:function(){return this.active&&!this.active.nextAll(".ui-menu-item").length},move:function(a,b,f){if(this.active){a=this.active[a+"All"](".ui-menu-item").eq(0); +a.length?this.activate(f,a):this.activate(f,this.element.children(b))}else this.activate(f,this.element.children(b))},nextPage:function(a){if(this.hasScroll())if(!this.active||this.last())this.activate(a,this.element.children(".ui-menu-item:first"));else{var b=this.active.offset().top,f=this.element.height(),c=this.element.children(".ui-menu-item").filter(function(){var e=d(this).offset().top-b-f+d(this).height();return e<10&&e>-10});c.length||(c=this.element.children(".ui-menu-item:last"));this.activate(a, +c)}else this.activate(a,this.element.children(".ui-menu-item").filter(!this.active||this.last()?":first":":last"))},previousPage:function(a){if(this.hasScroll())if(!this.active||this.first())this.activate(a,this.element.children(".ui-menu-item:last"));else{var b=this.active.offset().top,f=this.element.height();result=this.element.children(".ui-menu-item").filter(function(){var c=d(this).offset().top-b+f-d(this).height();return c<10&&c>-10});result.length||(result=this.element.children(".ui-menu-item:first")); +this.activate(a,result)}else this.activate(a,this.element.children(".ui-menu-item").filter(!this.active||this.first()?":last":":first"))},hasScroll:function(){return this.element.height()").addClass("ui-button-text").html(this.options.label).appendTo(b.empty()).text(),d=this.options.icons,e=d.primary&&d.secondary;if(d.primary||d.secondary){b.addClass("ui-button-text-icon"+(e?"s":d.primary?"-primary":"-secondary"));d.primary&&b.prepend("");d.secondary&&b.append("");if(!this.options.text){b.addClass(e?"ui-button-icons-only":"ui-button-icon-only").removeClass("ui-button-text-icons ui-button-text-icon-primary ui-button-text-icon-secondary"); +this.hasTitle||b.attr("title",c)}}else b.addClass("ui-button-text-only")}}});a.widget("ui.buttonset",{options:{items:":button, :submit, :reset, :checkbox, :radio, a, :data(button)"},_create:function(){this.element.addClass("ui-buttonset")},_init:function(){this.refresh()},_setOption:function(b,c){b==="disabled"&&this.buttons.button("option",b,c);a.Widget.prototype._setOption.apply(this,arguments)},refresh:function(){this.buttons=this.element.find(this.options.items).filter(":ui-button").button("refresh").end().not(":ui-button").button().end().map(function(){return a(this).button("widget")[0]}).removeClass("ui-corner-all ui-corner-left ui-corner-right").filter(":first").addClass("ui-corner-left").end().filter(":last").addClass("ui-corner-right").end().end()}, +destroy:function(){this.element.removeClass("ui-buttonset");this.buttons.map(function(){return a(this).button("widget")[0]}).removeClass("ui-corner-left ui-corner-right").end().button("destroy");a.Widget.prototype.destroy.call(this)}})})(jQuery); +;/* + * jQuery UI Dialog 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Dialog + * + * Depends: + * jquery.ui.core.js + * jquery.ui.widget.js + * jquery.ui.button.js + * jquery.ui.draggable.js + * jquery.ui.mouse.js + * jquery.ui.position.js + * jquery.ui.resizable.js + */ +(function(c,j){var k={buttons:true,height:true,maxHeight:true,maxWidth:true,minHeight:true,minWidth:true,width:true},l={maxHeight:true,maxWidth:true,minHeight:true,minWidth:true};c.widget("ui.dialog",{options:{autoOpen:true,buttons:{},closeOnEscape:true,closeText:"close",dialogClass:"",draggable:true,hide:null,height:"auto",maxHeight:false,maxWidth:false,minHeight:150,minWidth:150,modal:false,position:{my:"center",at:"center",collision:"fit",using:function(a){var b=c(this).css(a).offset().top;b<0&& +c(this).css("top",a.top-b)}},resizable:true,show:null,stack:true,title:"",width:300,zIndex:1E3},_create:function(){this.originalTitle=this.element.attr("title");if(typeof this.originalTitle!=="string")this.originalTitle="";this.options.title=this.options.title||this.originalTitle;var a=this,b=a.options,d=b.title||" ",e=c.ui.dialog.getTitleId(a.element),g=(a.uiDialog=c("
    ")).appendTo(document.body).hide().addClass("ui-dialog ui-widget ui-widget-content ui-corner-all "+b.dialogClass).css({zIndex:b.zIndex}).attr("tabIndex", +-1).css("outline",0).keydown(function(i){if(b.closeOnEscape&&i.keyCode&&i.keyCode===c.ui.keyCode.ESCAPE){a.close(i);i.preventDefault()}}).attr({role:"dialog","aria-labelledby":e}).mousedown(function(i){a.moveToTop(false,i)});a.element.show().removeAttr("title").addClass("ui-dialog-content ui-widget-content").appendTo(g);var f=(a.uiDialogTitlebar=c("
    ")).addClass("ui-dialog-titlebar ui-widget-header ui-corner-all ui-helper-clearfix").prependTo(g),h=c('').addClass("ui-dialog-titlebar-close ui-corner-all").attr("role", +"button").hover(function(){h.addClass("ui-state-hover")},function(){h.removeClass("ui-state-hover")}).focus(function(){h.addClass("ui-state-focus")}).blur(function(){h.removeClass("ui-state-focus")}).click(function(i){a.close(i);return false}).appendTo(f);(a.uiDialogTitlebarCloseText=c("")).addClass("ui-icon ui-icon-closethick").text(b.closeText).appendTo(h);c("").addClass("ui-dialog-title").attr("id",e).html(d).prependTo(f);if(c.isFunction(b.beforeclose)&&!c.isFunction(b.beforeClose))b.beforeClose= +b.beforeclose;f.find("*").add(f).disableSelection();b.draggable&&c.fn.draggable&&a._makeDraggable();b.resizable&&c.fn.resizable&&a._makeResizable();a._createButtons(b.buttons);a._isOpen=false;c.fn.bgiframe&&g.bgiframe()},_init:function(){this.options.autoOpen&&this.open()},destroy:function(){var a=this;a.overlay&&a.overlay.destroy();a.uiDialog.hide();a.element.unbind(".dialog").removeData("dialog").removeClass("ui-dialog-content ui-widget-content").hide().appendTo("body");a.uiDialog.remove();a.originalTitle&& +a.element.attr("title",a.originalTitle);return a},widget:function(){return this.uiDialog},close:function(a){var b=this,d,e;if(false!==b._trigger("beforeClose",a)){b.overlay&&b.overlay.destroy();b.uiDialog.unbind("keypress.ui-dialog");b._isOpen=false;if(b.options.hide)b.uiDialog.hide(b.options.hide,function(){b._trigger("close",a)});else{b.uiDialog.hide();b._trigger("close",a)}c.ui.dialog.overlay.resize();if(b.options.modal){d=0;c(".ui-dialog").each(function(){if(this!==b.uiDialog[0]){e=c(this).css("z-index"); +isNaN(e)||(d=Math.max(d,e))}});c.ui.dialog.maxZ=d}return b}},isOpen:function(){return this._isOpen},moveToTop:function(a,b){var d=this,e=d.options;if(e.modal&&!a||!e.stack&&!e.modal)return d._trigger("focus",b);if(e.zIndex>c.ui.dialog.maxZ)c.ui.dialog.maxZ=e.zIndex;if(d.overlay){c.ui.dialog.maxZ+=1;d.overlay.$el.css("z-index",c.ui.dialog.overlay.maxZ=c.ui.dialog.maxZ)}a={scrollTop:d.element.attr("scrollTop"),scrollLeft:d.element.attr("scrollLeft")};c.ui.dialog.maxZ+=1;d.uiDialog.css("z-index",c.ui.dialog.maxZ); +d.element.attr(a);d._trigger("focus",b);return d},open:function(){if(!this._isOpen){var a=this,b=a.options,d=a.uiDialog;a.overlay=b.modal?new c.ui.dialog.overlay(a):null;a._size();a._position(b.position);d.show(b.show);a.moveToTop(true);b.modal&&d.bind("keypress.ui-dialog",function(e){if(e.keyCode===c.ui.keyCode.TAB){var g=c(":tabbable",this),f=g.filter(":first");g=g.filter(":last");if(e.target===g[0]&&!e.shiftKey){f.focus(1);return false}else if(e.target===f[0]&&e.shiftKey){g.focus(1);return false}}}); +c(a.element.find(":tabbable").get().concat(d.find(".ui-dialog-buttonpane :tabbable").get().concat(d.get()))).eq(0).focus();a._isOpen=true;a._trigger("open");return a}},_createButtons:function(a){var b=this,d=false,e=c("
    ").addClass("ui-dialog-buttonpane ui-widget-content ui-helper-clearfix"),g=c("
    ").addClass("ui-dialog-buttonset").appendTo(e);b.uiDialog.find(".ui-dialog-buttonpane").remove();typeof a==="object"&&a!==null&&c.each(a,function(){return!(d=true)});if(d){c.each(a,function(f, +h){h=c.isFunction(h)?{click:h,text:f}:h;f=c('').attr(h,true).unbind("click").click(function(){h.click.apply(b.element[0],arguments)}).appendTo(g);c.fn.button&&f.button()});e.appendTo(b.uiDialog)}},_makeDraggable:function(){function a(f){return{position:f.position,offset:f.offset}}var b=this,d=b.options,e=c(document),g;b.uiDialog.draggable({cancel:".ui-dialog-content, .ui-dialog-titlebar-close",handle:".ui-dialog-titlebar",containment:"document",start:function(f,h){g= +d.height==="auto"?"auto":c(this).height();c(this).height(c(this).height()).addClass("ui-dialog-dragging");b._trigger("dragStart",f,a(h))},drag:function(f,h){b._trigger("drag",f,a(h))},stop:function(f,h){d.position=[h.position.left-e.scrollLeft(),h.position.top-e.scrollTop()];c(this).removeClass("ui-dialog-dragging").height(g);b._trigger("dragStop",f,a(h));c.ui.dialog.overlay.resize()}})},_makeResizable:function(a){function b(f){return{originalPosition:f.originalPosition,originalSize:f.originalSize, +position:f.position,size:f.size}}a=a===j?this.options.resizable:a;var d=this,e=d.options,g=d.uiDialog.css("position");a=typeof a==="string"?a:"n,e,s,w,se,sw,ne,nw";d.uiDialog.resizable({cancel:".ui-dialog-content",containment:"document",alsoResize:d.element,maxWidth:e.maxWidth,maxHeight:e.maxHeight,minWidth:e.minWidth,minHeight:d._minHeight(),handles:a,start:function(f,h){c(this).addClass("ui-dialog-resizing");d._trigger("resizeStart",f,b(h))},resize:function(f,h){d._trigger("resize",f,b(h))},stop:function(f, +h){c(this).removeClass("ui-dialog-resizing");e.height=c(this).height();e.width=c(this).width();d._trigger("resizeStop",f,b(h));c.ui.dialog.overlay.resize()}}).css("position",g).find(".ui-resizable-se").addClass("ui-icon ui-icon-grip-diagonal-se")},_minHeight:function(){var a=this.options;return a.height==="auto"?a.minHeight:Math.min(a.minHeight,a.height)},_position:function(a){var b=[],d=[0,0],e;if(a){if(typeof a==="string"||typeof a==="object"&&"0"in a){b=a.split?a.split(" "):[a[0],a[1]];if(b.length=== +1)b[1]=b[0];c.each(["left","top"],function(g,f){if(+b[g]===b[g]){d[g]=b[g];b[g]=f}});a={my:b.join(" "),at:b.join(" "),offset:d.join(" ")}}a=c.extend({},c.ui.dialog.prototype.options.position,a)}else a=c.ui.dialog.prototype.options.position;(e=this.uiDialog.is(":visible"))||this.uiDialog.show();this.uiDialog.css({top:0,left:0}).position(c.extend({of:window},a));e||this.uiDialog.hide()},_setOptions:function(a){var b=this,d={},e=false;c.each(a,function(g,f){b._setOption(g,f);if(g in k)e=true;if(g in +l)d[g]=f});e&&this._size();this.uiDialog.is(":data(resizable)")&&this.uiDialog.resizable("option",d)},_setOption:function(a,b){var d=this,e=d.uiDialog;switch(a){case "beforeclose":a="beforeClose";break;case "buttons":d._createButtons(b);break;case "closeText":d.uiDialogTitlebarCloseText.text(""+b);break;case "dialogClass":e.removeClass(d.options.dialogClass).addClass("ui-dialog ui-widget ui-widget-content ui-corner-all "+b);break;case "disabled":b?e.addClass("ui-dialog-disabled"):e.removeClass("ui-dialog-disabled"); +break;case "draggable":var g=e.is(":data(draggable)");g&&!b&&e.draggable("destroy");!g&&b&&d._makeDraggable();break;case "position":d._position(b);break;case "resizable":(g=e.is(":data(resizable)"))&&!b&&e.resizable("destroy");g&&typeof b==="string"&&e.resizable("option","handles",b);!g&&b!==false&&d._makeResizable(b);break;case "title":c(".ui-dialog-title",d.uiDialogTitlebar).html(""+(b||" "));break}c.Widget.prototype._setOption.apply(d,arguments)},_size:function(){var a=this.options,b,d,e= +this.uiDialog.is(":visible");this.element.show().css({width:"auto",minHeight:0,height:0});if(a.minWidth>a.width)a.width=a.minWidth;b=this.uiDialog.css({height:"auto",width:a.width}).height();d=Math.max(0,a.minHeight-b);if(a.height==="auto")if(c.support.minHeight)this.element.css({minHeight:d,height:"auto"});else{this.uiDialog.show();a=this.element.css("height","auto").height();e||this.uiDialog.hide();this.element.height(Math.max(a,d))}else this.element.height(Math.max(a.height-b,0));this.uiDialog.is(":data(resizable)")&& +this.uiDialog.resizable("option","minHeight",this._minHeight())}});c.extend(c.ui.dialog,{version:"1.8.7",uuid:0,maxZ:0,getTitleId:function(a){a=a.attr("id");if(!a){this.uuid+=1;a=this.uuid}return"ui-dialog-title-"+a},overlay:function(a){this.$el=c.ui.dialog.overlay.create(a)}});c.extend(c.ui.dialog.overlay,{instances:[],oldInstances:[],maxZ:0,events:c.map("focus,mousedown,mouseup,keydown,keypress,click".split(","),function(a){return a+".dialog-overlay"}).join(" "),create:function(a){if(this.instances.length=== +0){setTimeout(function(){c.ui.dialog.overlay.instances.length&&c(document).bind(c.ui.dialog.overlay.events,function(d){if(c(d.target).zIndex()").addClass("ui-widget-overlay")).appendTo(document.body).css({width:this.width(), +height:this.height()});c.fn.bgiframe&&b.bgiframe();this.instances.push(b);return b},destroy:function(a){var b=c.inArray(a,this.instances);b!=-1&&this.oldInstances.push(this.instances.splice(b,1)[0]);this.instances.length===0&&c([document,window]).unbind(".dialog-overlay");a.remove();var d=0;c.each(this.instances,function(){d=Math.max(d,this.css("z-index"))});this.maxZ=d},height:function(){var a,b;if(c.browser.msie&&c.browser.version<7){a=Math.max(document.documentElement.scrollHeight,document.body.scrollHeight); +b=Math.max(document.documentElement.offsetHeight,document.body.offsetHeight);return a");if(!a.values)a.values=[this._valueMin(),this._valueMin()];if(a.values.length&&a.values.length!==2)a.values=[a.values[0],a.values[0]]}else this.range=d("
    ");this.range.appendTo(this.element).addClass("ui-slider-range");if(a.range==="min"||a.range==="max")this.range.addClass("ui-slider-range-"+a.range);this.range.addClass("ui-widget-header")}d(".ui-slider-handle",this.element).length===0&&d("").appendTo(this.element).addClass("ui-slider-handle"); +if(a.values&&a.values.length)for(;d(".ui-slider-handle",this.element).length").appendTo(this.element).addClass("ui-slider-handle");this.handles=d(".ui-slider-handle",this.element).addClass("ui-state-default ui-corner-all");this.handle=this.handles.eq(0);this.handles.add(this.range).filter("a").click(function(c){c.preventDefault()}).hover(function(){a.disabled||d(this).addClass("ui-state-hover")},function(){d(this).removeClass("ui-state-hover")}).focus(function(){if(a.disabled)d(this).blur(); +else{d(".ui-slider .ui-state-focus").removeClass("ui-state-focus");d(this).addClass("ui-state-focus")}}).blur(function(){d(this).removeClass("ui-state-focus")});this.handles.each(function(c){d(this).data("index.ui-slider-handle",c)});this.handles.keydown(function(c){var e=true,f=d(this).data("index.ui-slider-handle"),h,g,i;if(!b.options.disabled){switch(c.keyCode){case d.ui.keyCode.HOME:case d.ui.keyCode.END:case d.ui.keyCode.PAGE_UP:case d.ui.keyCode.PAGE_DOWN:case d.ui.keyCode.UP:case d.ui.keyCode.RIGHT:case d.ui.keyCode.DOWN:case d.ui.keyCode.LEFT:e= +false;if(!b._keySliding){b._keySliding=true;d(this).addClass("ui-state-active");h=b._start(c,f);if(h===false)return}break}i=b.options.step;h=b.options.values&&b.options.values.length?(g=b.values(f)):(g=b.value());switch(c.keyCode){case d.ui.keyCode.HOME:g=b._valueMin();break;case d.ui.keyCode.END:g=b._valueMax();break;case d.ui.keyCode.PAGE_UP:g=b._trimAlignValue(h+(b._valueMax()-b._valueMin())/5);break;case d.ui.keyCode.PAGE_DOWN:g=b._trimAlignValue(h-(b._valueMax()-b._valueMin())/5);break;case d.ui.keyCode.UP:case d.ui.keyCode.RIGHT:if(h=== +b._valueMax())return;g=b._trimAlignValue(h+i);break;case d.ui.keyCode.DOWN:case d.ui.keyCode.LEFT:if(h===b._valueMin())return;g=b._trimAlignValue(h-i);break}b._slide(c,f,g);return e}}).keyup(function(c){var e=d(this).data("index.ui-slider-handle");if(b._keySliding){b._keySliding=false;b._stop(c,e);b._change(c,e);d(this).removeClass("ui-state-active")}});this._refreshValue();this._animateOff=false},destroy:function(){this.handles.remove();this.range.remove();this.element.removeClass("ui-slider ui-slider-horizontal ui-slider-vertical ui-slider-disabled ui-widget ui-widget-content ui-corner-all").removeData("slider").unbind(".slider"); +this._mouseDestroy();return this},_mouseCapture:function(b){var a=this.options,c,e,f,h,g;if(a.disabled)return false;this.elementSize={width:this.element.outerWidth(),height:this.element.outerHeight()};this.elementOffset=this.element.offset();c=this._normValueFromMouse({x:b.pageX,y:b.pageY});e=this._valueMax()-this._valueMin()+1;h=this;this.handles.each(function(i){var j=Math.abs(c-h.values(i));if(e>j){e=j;f=d(this);g=i}});if(a.range===true&&this.values(1)===a.min){g+=1;f=d(this.handles[g])}if(this._start(b, +g)===false)return false;this._mouseSliding=true;h._handleIndex=g;f.addClass("ui-state-active").focus();a=f.offset();this._clickOffset=!d(b.target).parents().andSelf().is(".ui-slider-handle")?{left:0,top:0}:{left:b.pageX-a.left-f.width()/2,top:b.pageY-a.top-f.height()/2-(parseInt(f.css("borderTopWidth"),10)||0)-(parseInt(f.css("borderBottomWidth"),10)||0)+(parseInt(f.css("marginTop"),10)||0)};this.handles.hasClass("ui-state-hover")||this._slide(b,g,c);return this._animateOff=true},_mouseStart:function(){return true}, +_mouseDrag:function(b){var a=this._normValueFromMouse({x:b.pageX,y:b.pageY});this._slide(b,this._handleIndex,a);return false},_mouseStop:function(b){this.handles.removeClass("ui-state-active");this._mouseSliding=false;this._stop(b,this._handleIndex);this._change(b,this._handleIndex);this._clickOffset=this._handleIndex=null;return this._animateOff=false},_detectOrientation:function(){this.orientation=this.options.orientation==="vertical"?"vertical":"horizontal"},_normValueFromMouse:function(b){var a; +if(this.orientation==="horizontal"){a=this.elementSize.width;b=b.x-this.elementOffset.left-(this._clickOffset?this._clickOffset.left:0)}else{a=this.elementSize.height;b=b.y-this.elementOffset.top-(this._clickOffset?this._clickOffset.top:0)}a=b/a;if(a>1)a=1;if(a<0)a=0;if(this.orientation==="vertical")a=1-a;b=this._valueMax()-this._valueMin();return this._trimAlignValue(this._valueMin()+a*b)},_start:function(b,a){var c={handle:this.handles[a],value:this.value()};if(this.options.values&&this.options.values.length){c.value= +this.values(a);c.values=this.values()}return this._trigger("start",b,c)},_slide:function(b,a,c){var e;if(this.options.values&&this.options.values.length){e=this.values(a?0:1);if(this.options.values.length===2&&this.options.range===true&&(a===0&&c>e||a===1&&c1){this.options.values[b]=this._trimAlignValue(a);this._refreshValue();this._change(null,b)}if(arguments.length)if(d.isArray(arguments[0])){c=this.options.values;e=arguments[0];for(f=0;f=this._valueMax())return this._valueMax();var a=this.options.step>0?this.options.step:1,c=(b-this._valueMin())%a;alignValue=b-c;if(Math.abs(c)*2>=a)alignValue+=c>0?a:-a;return parseFloat(alignValue.toFixed(5))},_valueMin:function(){return this.options.min},_valueMax:function(){return this.options.max}, +_refreshValue:function(){var b=this.options.range,a=this.options,c=this,e=!this._animateOff?a.animate:false,f,h={},g,i,j,l;if(this.options.values&&this.options.values.length)this.handles.each(function(k){f=(c.values(k)-c._valueMin())/(c._valueMax()-c._valueMin())*100;h[c.orientation==="horizontal"?"left":"bottom"]=f+"%";d(this).stop(1,1)[e?"animate":"css"](h,a.animate);if(c.options.range===true)if(c.orientation==="horizontal"){if(k===0)c.range.stop(1,1)[e?"animate":"css"]({left:f+"%"},a.animate); +if(k===1)c.range[e?"animate":"css"]({width:f-g+"%"},{queue:false,duration:a.animate})}else{if(k===0)c.range.stop(1,1)[e?"animate":"css"]({bottom:f+"%"},a.animate);if(k===1)c.range[e?"animate":"css"]({height:f-g+"%"},{queue:false,duration:a.animate})}g=f});else{i=this.value();j=this._valueMin();l=this._valueMax();f=l!==j?(i-j)/(l-j)*100:0;h[c.orientation==="horizontal"?"left":"bottom"]=f+"%";this.handle.stop(1,1)[e?"animate":"css"](h,a.animate);if(b==="min"&&this.orientation==="horizontal")this.range.stop(1, +1)[e?"animate":"css"]({width:f+"%"},a.animate);if(b==="max"&&this.orientation==="horizontal")this.range[e?"animate":"css"]({width:100-f+"%"},{queue:false,duration:a.animate});if(b==="min"&&this.orientation==="vertical")this.range.stop(1,1)[e?"animate":"css"]({height:f+"%"},a.animate);if(b==="max"&&this.orientation==="vertical")this.range[e?"animate":"css"]({height:100-f+"%"},{queue:false,duration:a.animate})}}});d.extend(d.ui.slider,{version:"1.8.7"})})(jQuery); +;/* + * jQuery UI Tabs 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Tabs + * + * Depends: + * jquery.ui.core.js + * jquery.ui.widget.js + */ +(function(d,p){function u(){return++v}function w(){return++x}var v=0,x=0;d.widget("ui.tabs",{options:{add:null,ajaxOptions:null,cache:false,cookie:null,collapsible:false,disable:null,disabled:[],enable:null,event:"click",fx:null,idPrefix:"ui-tabs-",load:null,panelTemplate:"
    ",remove:null,select:null,show:null,spinner:"Loading…",tabTemplate:"
  • #{label}
  • "},_create:function(){this._tabify(true)},_setOption:function(b,e){if(b=="selected")this.options.collapsible&& +e==this.options.selected||this.select(e);else{this.options[b]=e;this._tabify()}},_tabId:function(b){return b.title&&b.title.replace(/\s/g,"_").replace(/[^\w\u00c0-\uFFFF-]/g,"")||this.options.idPrefix+u()},_sanitizeSelector:function(b){return b.replace(/:/g,"\\:")},_cookie:function(){var b=this.cookie||(this.cookie=this.options.cookie.name||"ui-tabs-"+w());return d.cookie.apply(null,[b].concat(d.makeArray(arguments)))},_ui:function(b,e){return{tab:b,panel:e,index:this.anchors.index(b)}},_cleanup:function(){this.lis.filter(".ui-state-processing").removeClass("ui-state-processing").find("span:data(label.tabs)").each(function(){var b= +d(this);b.html(b.data("label.tabs")).removeData("label.tabs")})},_tabify:function(b){function e(g,f){g.css("display","");!d.support.opacity&&f.opacity&&g[0].style.removeAttribute("filter")}var a=this,c=this.options,h=/^#.+/;this.list=this.element.find("ol,ul").eq(0);this.lis=d(" > li:has(a[href])",this.list);this.anchors=this.lis.map(function(){return d("a",this)[0]});this.panels=d([]);this.anchors.each(function(g,f){var i=d(f).attr("href"),l=i.split("#")[0],q;if(l&&(l===location.toString().split("#")[0]|| +(q=d("base")[0])&&l===q.href)){i=f.hash;f.href=i}if(h.test(i))a.panels=a.panels.add(a.element.find(a._sanitizeSelector(i)));else if(i&&i!=="#"){d.data(f,"href.tabs",i);d.data(f,"load.tabs",i.replace(/#.*$/,""));i=a._tabId(f);f.href="#"+i;f=a.element.find("#"+i);if(!f.length){f=d(c.panelTemplate).attr("id",i).addClass("ui-tabs-panel ui-widget-content ui-corner-bottom").insertAfter(a.panels[g-1]||a.list);f.data("destroy.tabs",true)}a.panels=a.panels.add(f)}else c.disabled.push(g)});if(b){this.element.addClass("ui-tabs ui-widget ui-widget-content ui-corner-all"); +this.list.addClass("ui-tabs-nav ui-helper-reset ui-helper-clearfix ui-widget-header ui-corner-all");this.lis.addClass("ui-state-default ui-corner-top");this.panels.addClass("ui-tabs-panel ui-widget-content ui-corner-bottom");if(c.selected===p){location.hash&&this.anchors.each(function(g,f){if(f.hash==location.hash){c.selected=g;return false}});if(typeof c.selected!=="number"&&c.cookie)c.selected=parseInt(a._cookie(),10);if(typeof c.selected!=="number"&&this.lis.filter(".ui-tabs-selected").length)c.selected= +this.lis.index(this.lis.filter(".ui-tabs-selected"));c.selected=c.selected||(this.lis.length?0:-1)}else if(c.selected===null)c.selected=-1;c.selected=c.selected>=0&&this.anchors[c.selected]||c.selected<0?c.selected:0;c.disabled=d.unique(c.disabled.concat(d.map(this.lis.filter(".ui-state-disabled"),function(g){return a.lis.index(g)}))).sort();d.inArray(c.selected,c.disabled)!=-1&&c.disabled.splice(d.inArray(c.selected,c.disabled),1);this.panels.addClass("ui-tabs-hide");this.lis.removeClass("ui-tabs-selected ui-state-active"); +if(c.selected>=0&&this.anchors.length){a.element.find(a._sanitizeSelector(a.anchors[c.selected].hash)).removeClass("ui-tabs-hide");this.lis.eq(c.selected).addClass("ui-tabs-selected ui-state-active");a.element.queue("tabs",function(){a._trigger("show",null,a._ui(a.anchors[c.selected],a.element.find(a._sanitizeSelector(a.anchors[c.selected].hash))))});this.load(c.selected)}d(window).bind("unload",function(){a.lis.add(a.anchors).unbind(".tabs");a.lis=a.anchors=a.panels=null})}else c.selected=this.lis.index(this.lis.filter(".ui-tabs-selected")); +this.element[c.collapsible?"addClass":"removeClass"]("ui-tabs-collapsible");c.cookie&&this._cookie(c.selected,c.cookie);b=0;for(var j;j=this.lis[b];b++)d(j)[d.inArray(b,c.disabled)!=-1&&!d(j).hasClass("ui-tabs-selected")?"addClass":"removeClass"]("ui-state-disabled");c.cache===false&&this.anchors.removeData("cache.tabs");this.lis.add(this.anchors).unbind(".tabs");if(c.event!=="mouseover"){var k=function(g,f){f.is(":not(.ui-state-disabled)")&&f.addClass("ui-state-"+g)},n=function(g,f){f.removeClass("ui-state-"+ +g)};this.lis.bind("mouseover.tabs",function(){k("hover",d(this))});this.lis.bind("mouseout.tabs",function(){n("hover",d(this))});this.anchors.bind("focus.tabs",function(){k("focus",d(this).closest("li"))});this.anchors.bind("blur.tabs",function(){n("focus",d(this).closest("li"))})}var m,o;if(c.fx)if(d.isArray(c.fx)){m=c.fx[0];o=c.fx[1]}else m=o=c.fx;var r=o?function(g,f){d(g).closest("li").addClass("ui-tabs-selected ui-state-active");f.hide().removeClass("ui-tabs-hide").animate(o,o.duration||"normal", +function(){e(f,o);a._trigger("show",null,a._ui(g,f[0]))})}:function(g,f){d(g).closest("li").addClass("ui-tabs-selected ui-state-active");f.removeClass("ui-tabs-hide");a._trigger("show",null,a._ui(g,f[0]))},s=m?function(g,f){f.animate(m,m.duration||"normal",function(){a.lis.removeClass("ui-tabs-selected ui-state-active");f.addClass("ui-tabs-hide");e(f,m);a.element.dequeue("tabs")})}:function(g,f){a.lis.removeClass("ui-tabs-selected ui-state-active");f.addClass("ui-tabs-hide");a.element.dequeue("tabs")}; +this.anchors.bind(c.event+".tabs",function(){var g=this,f=d(g).closest("li"),i=a.panels.filter(":not(.ui-tabs-hide)"),l=a.element.find(a._sanitizeSelector(g.hash));if(f.hasClass("ui-tabs-selected")&&!c.collapsible||f.hasClass("ui-state-disabled")||f.hasClass("ui-state-processing")||a.panels.filter(":animated").length||a._trigger("select",null,a._ui(this,l[0]))===false){this.blur();return false}c.selected=a.anchors.index(this);a.abort();if(c.collapsible)if(f.hasClass("ui-tabs-selected")){c.selected= +-1;c.cookie&&a._cookie(c.selected,c.cookie);a.element.queue("tabs",function(){s(g,i)}).dequeue("tabs");this.blur();return false}else if(!i.length){c.cookie&&a._cookie(c.selected,c.cookie);a.element.queue("tabs",function(){r(g,l)});a.load(a.anchors.index(this));this.blur();return false}c.cookie&&a._cookie(c.selected,c.cookie);if(l.length){i.length&&a.element.queue("tabs",function(){s(g,i)});a.element.queue("tabs",function(){r(g,l)});a.load(a.anchors.index(this))}else throw"jQuery UI Tabs: Mismatching fragment identifier."; +d.browser.msie&&this.blur()});this.anchors.bind("click.tabs",function(){return false})},_getIndex:function(b){if(typeof b=="string")b=this.anchors.index(this.anchors.filter("[href$="+b+"]"));return b},destroy:function(){var b=this.options;this.abort();this.element.unbind(".tabs").removeClass("ui-tabs ui-widget ui-widget-content ui-corner-all ui-tabs-collapsible").removeData("tabs");this.list.removeClass("ui-tabs-nav ui-helper-reset ui-helper-clearfix ui-widget-header ui-corner-all");this.anchors.each(function(){var e= +d.data(this,"href.tabs");if(e)this.href=e;var a=d(this).unbind(".tabs");d.each(["href","load","cache"],function(c,h){a.removeData(h+".tabs")})});this.lis.unbind(".tabs").add(this.panels).each(function(){d.data(this,"destroy.tabs")?d(this).remove():d(this).removeClass("ui-state-default ui-corner-top ui-tabs-selected ui-state-active ui-state-hover ui-state-focus ui-state-disabled ui-tabs-panel ui-widget-content ui-corner-bottom ui-tabs-hide")});b.cookie&&this._cookie(null,b.cookie);return this},add:function(b, +e,a){if(a===p)a=this.anchors.length;var c=this,h=this.options;e=d(h.tabTemplate.replace(/#\{href\}/g,b).replace(/#\{label\}/g,e));b=!b.indexOf("#")?b.replace("#",""):this._tabId(d("a",e)[0]);e.addClass("ui-state-default ui-corner-top").data("destroy.tabs",true);var j=c.element.find("#"+b);j.length||(j=d(h.panelTemplate).attr("id",b).data("destroy.tabs",true));j.addClass("ui-tabs-panel ui-widget-content ui-corner-bottom ui-tabs-hide");if(a>=this.lis.length){e.appendTo(this.list);j.appendTo(this.list[0].parentNode)}else{e.insertBefore(this.lis[a]); +j.insertBefore(this.panels[a])}h.disabled=d.map(h.disabled,function(k){return k>=a?++k:k});this._tabify();if(this.anchors.length==1){h.selected=0;e.addClass("ui-tabs-selected ui-state-active");j.removeClass("ui-tabs-hide");this.element.queue("tabs",function(){c._trigger("show",null,c._ui(c.anchors[0],c.panels[0]))});this.load(0)}this._trigger("add",null,this._ui(this.anchors[a],this.panels[a]));return this},remove:function(b){b=this._getIndex(b);var e=this.options,a=this.lis.eq(b).remove(),c=this.panels.eq(b).remove(); +if(a.hasClass("ui-tabs-selected")&&this.anchors.length>1)this.select(b+(b+1=b?--h:h});this._tabify();this._trigger("remove",null,this._ui(a.find("a")[0],c[0]));return this},enable:function(b){b=this._getIndex(b);var e=this.options;if(d.inArray(b,e.disabled)!=-1){this.lis.eq(b).removeClass("ui-state-disabled");e.disabled=d.grep(e.disabled,function(a){return a!=b});this._trigger("enable",null, +this._ui(this.anchors[b],this.panels[b]));return this}},disable:function(b){b=this._getIndex(b);var e=this.options;if(b!=e.selected){this.lis.eq(b).addClass("ui-state-disabled");e.disabled.push(b);e.disabled.sort();this._trigger("disable",null,this._ui(this.anchors[b],this.panels[b]))}return this},select:function(b){b=this._getIndex(b);if(b==-1)if(this.options.collapsible&&this.options.selected!=-1)b=this.options.selected;else return this;this.anchors.eq(b).trigger(this.options.event+".tabs");return this}, +load:function(b){b=this._getIndex(b);var e=this,a=this.options,c=this.anchors.eq(b)[0],h=d.data(c,"load.tabs");this.abort();if(!h||this.element.queue("tabs").length!==0&&d.data(c,"cache.tabs"))this.element.dequeue("tabs");else{this.lis.eq(b).addClass("ui-state-processing");if(a.spinner){var j=d("span",c);j.data("label.tabs",j.html()).html(a.spinner)}this.xhr=d.ajax(d.extend({},a.ajaxOptions,{url:h,success:function(k,n){e.element.find(e._sanitizeSelector(c.hash)).html(k);e._cleanup();a.cache&&d.data(c, +"cache.tabs",true);e._trigger("load",null,e._ui(e.anchors[b],e.panels[b]));try{a.ajaxOptions.success(k,n)}catch(m){}},error:function(k,n){e._cleanup();e._trigger("load",null,e._ui(e.anchors[b],e.panels[b]));try{a.ajaxOptions.error(k,n,b,c)}catch(m){}}}));e.element.dequeue("tabs");return this}},abort:function(){this.element.queue([]);this.panels.stop(false,true);this.element.queue("tabs",this.element.queue("tabs").splice(-2,2));if(this.xhr){this.xhr.abort();delete this.xhr}this._cleanup();return this}, +url:function(b,e){this.anchors.eq(b).removeData("cache.tabs").data("load.tabs",e);return this},length:function(){return this.anchors.length}});d.extend(d.ui.tabs,{version:"1.8.7"});d.extend(d.ui.tabs.prototype,{rotation:null,rotate:function(b,e){var a=this,c=this.options,h=a._rotate||(a._rotate=function(j){clearTimeout(a.rotation);a.rotation=setTimeout(function(){var k=c.selected;a.select(++k')}function E(a,b){d.extend(a,b);for(var c in b)if(b[c]== +null||b[c]==G)a[c]=b[c];return a}d.extend(d.ui,{datepicker:{version:"1.8.7"}});var y=(new Date).getTime();d.extend(K.prototype,{markerClassName:"hasDatepicker",log:function(){this.debug&&console.log.apply("",arguments)},_widgetDatepicker:function(){return this.dpDiv},setDefaults:function(a){E(this._defaults,a||{});return this},_attachDatepicker:function(a,b){var c=null;for(var e in this._defaults){var f=a.getAttribute("date:"+e);if(f){c=c||{};try{c[e]=eval(f)}catch(h){c[e]=f}}}e=a.nodeName.toLowerCase(); +f=e=="div"||e=="span";if(!a.id){this.uuid+=1;a.id="dp"+this.uuid}var i=this._newInst(d(a),f);i.settings=d.extend({},b||{},c||{});if(e=="input")this._connectDatepicker(a,i);else f&&this._inlineDatepicker(a,i)},_newInst:function(a,b){return{id:a[0].id.replace(/([^A-Za-z0-9_-])/g,"\\\\$1"),input:a,selectedDay:0,selectedMonth:0,selectedYear:0,drawMonth:0,drawYear:0,inline:b,dpDiv:!b?this.dpDiv:d('
    ')}}, +_connectDatepicker:function(a,b){var c=d(a);b.append=d([]);b.trigger=d([]);if(!c.hasClass(this.markerClassName)){this._attachments(c,b);c.addClass(this.markerClassName).keydown(this._doKeyDown).keypress(this._doKeyPress).keyup(this._doKeyUp).bind("setData.datepicker",function(e,f,h){b.settings[f]=h}).bind("getData.datepicker",function(e,f){return this._get(b,f)});this._autoSize(b);d.data(a,"datepicker",b)}},_attachments:function(a,b){var c=this._get(b,"appendText"),e=this._get(b,"isRTL");b.append&& +b.append.remove();if(c){b.append=d(''+c+"");a[e?"before":"after"](b.append)}a.unbind("focus",this._showDatepicker);b.trigger&&b.trigger.remove();c=this._get(b,"showOn");if(c=="focus"||c=="both")a.focus(this._showDatepicker);if(c=="button"||c=="both"){c=this._get(b,"buttonText");var f=this._get(b,"buttonImage");b.trigger=d(this._get(b,"buttonImageOnly")?d("").addClass(this._triggerClass).attr({src:f,alt:c,title:c}):d('').addClass(this._triggerClass).html(f== +""?c:d("").attr({src:f,alt:c,title:c})));a[e?"before":"after"](b.trigger);b.trigger.click(function(){d.datepicker._datepickerShowing&&d.datepicker._lastInput==a[0]?d.datepicker._hideDatepicker():d.datepicker._showDatepicker(a[0]);return false})}},_autoSize:function(a){if(this._get(a,"autoSize")&&!a.inline){var b=new Date(2009,11,20),c=this._get(a,"dateFormat");if(c.match(/[DM]/)){var e=function(f){for(var h=0,i=0,g=0;gh){h=f[g].length;i=g}return i};b.setMonth(e(this._get(a, +c.match(/MM/)?"monthNames":"monthNamesShort")));b.setDate(e(this._get(a,c.match(/DD/)?"dayNames":"dayNamesShort"))+20-b.getDay())}a.input.attr("size",this._formatDate(a,b).length)}},_inlineDatepicker:function(a,b){var c=d(a);if(!c.hasClass(this.markerClassName)){c.addClass(this.markerClassName).append(b.dpDiv).bind("setData.datepicker",function(e,f,h){b.settings[f]=h}).bind("getData.datepicker",function(e,f){return this._get(b,f)});d.data(a,"datepicker",b);this._setDate(b,this._getDefaultDate(b), +true);this._updateDatepicker(b);this._updateAlternate(b);b.dpDiv.show()}},_dialogDatepicker:function(a,b,c,e,f){a=this._dialogInst;if(!a){this.uuid+=1;this._dialogInput=d('');this._dialogInput.keydown(this._doKeyDown);d("body").append(this._dialogInput);a=this._dialogInst=this._newInst(this._dialogInput,false);a.settings={};d.data(this._dialogInput[0],"datepicker",a)}E(a.settings,e||{}); +b=b&&b.constructor==Date?this._formatDate(a,b):b;this._dialogInput.val(b);this._pos=f?f.length?f:[f.pageX,f.pageY]:null;if(!this._pos)this._pos=[document.documentElement.clientWidth/2-100+(document.documentElement.scrollLeft||document.body.scrollLeft),document.documentElement.clientHeight/2-150+(document.documentElement.scrollTop||document.body.scrollTop)];this._dialogInput.css("left",this._pos[0]+20+"px").css("top",this._pos[1]+"px");a.settings.onSelect=c;this._inDialog=true;this.dpDiv.addClass(this._dialogClass); +this._showDatepicker(this._dialogInput[0]);d.blockUI&&d.blockUI(this.dpDiv);d.data(this._dialogInput[0],"datepicker",a);return this},_destroyDatepicker:function(a){var b=d(a),c=d.data(a,"datepicker");if(b.hasClass(this.markerClassName)){var e=a.nodeName.toLowerCase();d.removeData(a,"datepicker");if(e=="input"){c.append.remove();c.trigger.remove();b.removeClass(this.markerClassName).unbind("focus",this._showDatepicker).unbind("keydown",this._doKeyDown).unbind("keypress",this._doKeyPress).unbind("keyup", +this._doKeyUp)}else if(e=="div"||e=="span")b.removeClass(this.markerClassName).empty()}},_enableDatepicker:function(a){var b=d(a),c=d.data(a,"datepicker");if(b.hasClass(this.markerClassName)){var e=a.nodeName.toLowerCase();if(e=="input"){a.disabled=false;c.trigger.filter("button").each(function(){this.disabled=false}).end().filter("img").css({opacity:"1.0",cursor:""})}else if(e=="div"||e=="span")b.children("."+this._inlineClass).children().removeClass("ui-state-disabled");this._disabledInputs=d.map(this._disabledInputs, +function(f){return f==a?null:f})}},_disableDatepicker:function(a){var b=d(a),c=d.data(a,"datepicker");if(b.hasClass(this.markerClassName)){var e=a.nodeName.toLowerCase();if(e=="input"){a.disabled=true;c.trigger.filter("button").each(function(){this.disabled=true}).end().filter("img").css({opacity:"0.5",cursor:"default"})}else if(e=="div"||e=="span")b.children("."+this._inlineClass).children().addClass("ui-state-disabled");this._disabledInputs=d.map(this._disabledInputs,function(f){return f==a?null: +f});this._disabledInputs[this._disabledInputs.length]=a}},_isDisabledDatepicker:function(a){if(!a)return false;for(var b=0;b-1}},_doKeyUp:function(a){a=d.datepicker._getInst(a.target);if(a.input.val()!=a.lastVal)try{if(d.datepicker.parseDate(d.datepicker._get(a,"dateFormat"),a.input?a.input.val():null,d.datepicker._getFormatConfig(a))){d.datepicker._setDateFromField(a);d.datepicker._updateAlternate(a);d.datepicker._updateDatepicker(a)}}catch(b){d.datepicker.log(b)}return true}, +_showDatepicker:function(a){a=a.target||a;if(a.nodeName.toLowerCase()!="input")a=d("input",a.parentNode)[0];if(!(d.datepicker._isDisabledDatepicker(a)||d.datepicker._lastInput==a)){var b=d.datepicker._getInst(a);d.datepicker._curInst&&d.datepicker._curInst!=b&&d.datepicker._curInst.dpDiv.stop(true,true);var c=d.datepicker._get(b,"beforeShow");E(b.settings,c?c.apply(a,[a,b]):{});b.lastVal=null;d.datepicker._lastInput=a;d.datepicker._setDateFromField(b);if(d.datepicker._inDialog)a.value="";if(!d.datepicker._pos){d.datepicker._pos= +d.datepicker._findPos(a);d.datepicker._pos[1]+=a.offsetHeight}var e=false;d(a).parents().each(function(){e|=d(this).css("position")=="fixed";return!e});if(e&&d.browser.opera){d.datepicker._pos[0]-=document.documentElement.scrollLeft;d.datepicker._pos[1]-=document.documentElement.scrollTop}c={left:d.datepicker._pos[0],top:d.datepicker._pos[1]};d.datepicker._pos=null;b.dpDiv.empty();b.dpDiv.css({position:"absolute",display:"block",top:"-1000px"});d.datepicker._updateDatepicker(b);c=d.datepicker._checkOffset(b, +c,e);b.dpDiv.css({position:d.datepicker._inDialog&&d.blockUI?"static":e?"fixed":"absolute",display:"none",left:c.left+"px",top:c.top+"px"});if(!b.inline){c=d.datepicker._get(b,"showAnim");var f=d.datepicker._get(b,"duration"),h=function(){d.datepicker._datepickerShowing=true;var i=b.dpDiv.find("iframe.ui-datepicker-cover");if(i.length){var g=d.datepicker._getBorders(b.dpDiv);i.css({left:-g[0],top:-g[1],width:b.dpDiv.outerWidth(),height:b.dpDiv.outerHeight()})}};b.dpDiv.zIndex(d(a).zIndex()+1);d.effects&& +d.effects[c]?b.dpDiv.show(c,d.datepicker._get(b,"showOptions"),f,h):b.dpDiv[c||"show"](c?f:null,h);if(!c||!f)h();b.input.is(":visible")&&!b.input.is(":disabled")&&b.input.focus();d.datepicker._curInst=b}}},_updateDatepicker:function(a){var b=this,c=d.datepicker._getBorders(a.dpDiv);a.dpDiv.empty().append(this._generateHTML(a));var e=a.dpDiv.find("iframe.ui-datepicker-cover");e.length&&e.css({left:-c[0],top:-c[1],width:a.dpDiv.outerWidth(),height:a.dpDiv.outerHeight()});a.dpDiv.find("button, .ui-datepicker-prev, .ui-datepicker-next, .ui-datepicker-calendar td a").bind("mouseout", +function(){d(this).removeClass("ui-state-hover");this.className.indexOf("ui-datepicker-prev")!=-1&&d(this).removeClass("ui-datepicker-prev-hover");this.className.indexOf("ui-datepicker-next")!=-1&&d(this).removeClass("ui-datepicker-next-hover")}).bind("mouseover",function(){if(!b._isDisabledDatepicker(a.inline?a.dpDiv.parent()[0]:a.input[0])){d(this).parents(".ui-datepicker-calendar").find("a").removeClass("ui-state-hover");d(this).addClass("ui-state-hover");this.className.indexOf("ui-datepicker-prev")!= +-1&&d(this).addClass("ui-datepicker-prev-hover");this.className.indexOf("ui-datepicker-next")!=-1&&d(this).addClass("ui-datepicker-next-hover")}}).end().find("."+this._dayOverClass+" a").trigger("mouseover").end();c=this._getNumberOfMonths(a);e=c[1];e>1?a.dpDiv.addClass("ui-datepicker-multi-"+e).css("width",17*e+"em"):a.dpDiv.removeClass("ui-datepicker-multi-2 ui-datepicker-multi-3 ui-datepicker-multi-4").width("");a.dpDiv[(c[0]!=1||c[1]!=1?"add":"remove")+"Class"]("ui-datepicker-multi");a.dpDiv[(this._get(a, +"isRTL")?"add":"remove")+"Class"]("ui-datepicker-rtl");a==d.datepicker._curInst&&d.datepicker._datepickerShowing&&a.input&&a.input.is(":visible")&&!a.input.is(":disabled")&&a.input.focus();if(a.yearshtml){var f=a.yearshtml;setTimeout(function(){f===a.yearshtml&&a.dpDiv.find("select.ui-datepicker-year:first").replaceWith(a.yearshtml);f=a.yearshtml=null},0)}},_getBorders:function(a){var b=function(c){return{thin:1,medium:2,thick:3}[c]||c};return[parseFloat(b(a.css("border-left-width"))),parseFloat(b(a.css("border-top-width")))]}, +_checkOffset:function(a,b,c){var e=a.dpDiv.outerWidth(),f=a.dpDiv.outerHeight(),h=a.input?a.input.outerWidth():0,i=a.input?a.input.outerHeight():0,g=document.documentElement.clientWidth+d(document).scrollLeft(),j=document.documentElement.clientHeight+d(document).scrollTop();b.left-=this._get(a,"isRTL")?e-h:0;b.left-=c&&b.left==a.input.offset().left?d(document).scrollLeft():0;b.top-=c&&b.top==a.input.offset().top+i?d(document).scrollTop():0;b.left-=Math.min(b.left,b.left+e>g&&g>e?Math.abs(b.left+e- +g):0);b.top-=Math.min(b.top,b.top+f>j&&j>f?Math.abs(f+i):0);return b},_findPos:function(a){for(var b=this._get(this._getInst(a),"isRTL");a&&(a.type=="hidden"||a.nodeType!=1);)a=a[b?"previousSibling":"nextSibling"];a=d(a).offset();return[a.left,a.top]},_hideDatepicker:function(a){var b=this._curInst;if(!(!b||a&&b!=d.data(a,"datepicker")))if(this._datepickerShowing){a=this._get(b,"showAnim");var c=this._get(b,"duration"),e=function(){d.datepicker._tidyDialog(b);this._curInst=null};d.effects&&d.effects[a]? +b.dpDiv.hide(a,d.datepicker._get(b,"showOptions"),c,e):b.dpDiv[a=="slideDown"?"slideUp":a=="fadeIn"?"fadeOut":"hide"](a?c:null,e);a||e();if(a=this._get(b,"onClose"))a.apply(b.input?b.input[0]:null,[b.input?b.input.val():"",b]);this._datepickerShowing=false;this._lastInput=null;if(this._inDialog){this._dialogInput.css({position:"absolute",left:"0",top:"-100px"});if(d.blockUI){d.unblockUI();d("body").append(this.dpDiv)}}this._inDialog=false}},_tidyDialog:function(a){a.dpDiv.removeClass(this._dialogClass).unbind(".ui-datepicker-calendar")}, +_checkExternalClick:function(a){if(d.datepicker._curInst){a=d(a.target);a[0].id!=d.datepicker._mainDivId&&a.parents("#"+d.datepicker._mainDivId).length==0&&!a.hasClass(d.datepicker.markerClassName)&&!a.hasClass(d.datepicker._triggerClass)&&d.datepicker._datepickerShowing&&!(d.datepicker._inDialog&&d.blockUI)&&d.datepicker._hideDatepicker()}},_adjustDate:function(a,b,c){a=d(a);var e=this._getInst(a[0]);if(!this._isDisabledDatepicker(a[0])){this._adjustInstDate(e,b+(c=="M"?this._get(e,"showCurrentAtPos"): +0),c);this._updateDatepicker(e)}},_gotoToday:function(a){a=d(a);var b=this._getInst(a[0]);if(this._get(b,"gotoCurrent")&&b.currentDay){b.selectedDay=b.currentDay;b.drawMonth=b.selectedMonth=b.currentMonth;b.drawYear=b.selectedYear=b.currentYear}else{var c=new Date;b.selectedDay=c.getDate();b.drawMonth=b.selectedMonth=c.getMonth();b.drawYear=b.selectedYear=c.getFullYear()}this._notifyChange(b);this._adjustDate(a)},_selectMonthYear:function(a,b,c){a=d(a);var e=this._getInst(a[0]);e._selectingMonthYear= +false;e["selected"+(c=="M"?"Month":"Year")]=e["draw"+(c=="M"?"Month":"Year")]=parseInt(b.options[b.selectedIndex].value,10);this._notifyChange(e);this._adjustDate(a)},_clickMonthYear:function(a){var b=this._getInst(d(a)[0]);b.input&&b._selectingMonthYear&&setTimeout(function(){b.input.focus()},0);b._selectingMonthYear=!b._selectingMonthYear},_selectDay:function(a,b,c,e){var f=d(a);if(!(d(e).hasClass(this._unselectableClass)||this._isDisabledDatepicker(f[0]))){f=this._getInst(f[0]);f.selectedDay=f.currentDay= +d("a",e).html();f.selectedMonth=f.currentMonth=b;f.selectedYear=f.currentYear=c;this._selectDate(a,this._formatDate(f,f.currentDay,f.currentMonth,f.currentYear))}},_clearDate:function(a){a=d(a);this._getInst(a[0]);this._selectDate(a,"")},_selectDate:function(a,b){a=this._getInst(d(a)[0]);b=b!=null?b:this._formatDate(a);a.input&&a.input.val(b);this._updateAlternate(a);var c=this._get(a,"onSelect");if(c)c.apply(a.input?a.input[0]:null,[b,a]);else a.input&&a.input.trigger("change");if(a.inline)this._updateDatepicker(a); +else{this._hideDatepicker();this._lastInput=a.input[0];typeof a.input[0]!="object"&&a.input.focus();this._lastInput=null}},_updateAlternate:function(a){var b=this._get(a,"altField");if(b){var c=this._get(a,"altFormat")||this._get(a,"dateFormat"),e=this._getDate(a),f=this.formatDate(c,e,this._getFormatConfig(a));d(b).each(function(){d(this).val(f)})}},noWeekends:function(a){a=a.getDay();return[a>0&&a<6,""]},iso8601Week:function(a){a=new Date(a.getTime());a.setDate(a.getDate()+4-(a.getDay()||7));var b= +a.getTime();a.setMonth(0);a.setDate(1);return Math.floor(Math.round((b-a)/864E5)/7)+1},parseDate:function(a,b,c){if(a==null||b==null)throw"Invalid arguments";b=typeof b=="object"?b.toString():b+"";if(b=="")return null;for(var e=(c?c.shortYearCutoff:null)||this._defaults.shortYearCutoff,f=(c?c.dayNamesShort:null)||this._defaults.dayNamesShort,h=(c?c.dayNames:null)||this._defaults.dayNames,i=(c?c.monthNamesShort:null)||this._defaults.monthNamesShort,g=(c?c.monthNames:null)||this._defaults.monthNames, +j=c=-1,l=-1,u=-1,k=false,o=function(p){(p=z+1-1){j=1;l=u;do{e=this._getDaysInMonth(c,j-1);if(l<=e)break;j++;l-=e}while(1)}w=this._daylightSavingAdjust(new Date(c,j-1,l));if(w.getFullYear()!=c||w.getMonth()+1!=j||w.getDate()!=l)throw"Invalid date";return w},ATOM:"yy-mm-dd",COOKIE:"D, dd M yy",ISO_8601:"yy-mm-dd",RFC_822:"D, d M y",RFC_850:"DD, dd-M-y",RFC_1036:"D, d M y", +RFC_1123:"D, d M yy",RFC_2822:"D, d M yy",RSS:"D, d M y",TICKS:"!",TIMESTAMP:"@",W3C:"yy-mm-dd",_ticksTo1970:(718685+Math.floor(492.5)-Math.floor(19.7)+Math.floor(4.925))*24*60*60*1E7,formatDate:function(a,b,c){if(!b)return"";var e=(c?c.dayNamesShort:null)||this._defaults.dayNamesShort,f=(c?c.dayNames:null)||this._defaults.dayNames,h=(c?c.monthNamesShort:null)||this._defaults.monthNamesShort;c=(c?c.monthNames:null)||this._defaults.monthNames;var i=function(o){(o=k+112?a.getHours()+2:0);return a},_setDate:function(a,b,c){var e=!b,f=a.selectedMonth,h=a.selectedYear;b=this._restrictMinMax(a,this._determineDate(a,b,new Date));a.selectedDay= +a.currentDay=b.getDate();a.drawMonth=a.selectedMonth=a.currentMonth=b.getMonth();a.drawYear=a.selectedYear=a.currentYear=b.getFullYear();if((f!=a.selectedMonth||h!=a.selectedYear)&&!c)this._notifyChange(a);this._adjustInstDate(a);if(a.input)a.input.val(e?"":this._formatDate(a))},_getDate:function(a){return!a.currentYear||a.input&&a.input.val()==""?null:this._daylightSavingAdjust(new Date(a.currentYear,a.currentMonth,a.currentDay))},_generateHTML:function(a){var b=new Date;b=this._daylightSavingAdjust(new Date(b.getFullYear(), +b.getMonth(),b.getDate()));var c=this._get(a,"isRTL"),e=this._get(a,"showButtonPanel"),f=this._get(a,"hideIfNoPrevNext"),h=this._get(a,"navigationAsDateFormat"),i=this._getNumberOfMonths(a),g=this._get(a,"showCurrentAtPos"),j=this._get(a,"stepMonths"),l=i[0]!=1||i[1]!=1,u=this._daylightSavingAdjust(!a.currentDay?new Date(9999,9,9):new Date(a.currentYear,a.currentMonth,a.currentDay)),k=this._getMinMaxDate(a,"min"),o=this._getMinMaxDate(a,"max");g=a.drawMonth-g;var m=a.drawYear;if(g<0){g+=12;m--}if(o){var n= +this._daylightSavingAdjust(new Date(o.getFullYear(),o.getMonth()-i[0]*i[1]+1,o.getDate()));for(n=k&&nn;){g--;if(g<0){g=11;m--}}}a.drawMonth=g;a.drawYear=m;n=this._get(a,"prevText");n=!h?n:this.formatDate(n,this._daylightSavingAdjust(new Date(m,g-j,1)),this._getFormatConfig(a));n=this._canAdjustMonth(a,-1,m,g)?''+n+"":f?"":''+n+"";var r=this._get(a,"nextText");r=!h?r:this.formatDate(r,this._daylightSavingAdjust(new Date(m,g+j,1)),this._getFormatConfig(a));f=this._canAdjustMonth(a,+1,m,g)?''+r+"":f?"":''+r+"";j=this._get(a,"currentText");r=this._get(a,"gotoCurrent")&&a.currentDay?u:b;j=!h?j:this.formatDate(j,r,this._getFormatConfig(a));h=!a.inline?'":"";e=e?'
    '+(c?h:"")+(this._isInRange(a,r)?'":"")+(c?"":h)+"
    ":"";h=parseInt(this._get(a,"firstDay"),10);h=isNaN(h)?0:h;j=this._get(a,"showWeek");r=this._get(a,"dayNames");this._get(a,"dayNamesShort");var s=this._get(a,"dayNamesMin"),z= +this._get(a,"monthNames"),w=this._get(a,"monthNamesShort"),p=this._get(a,"beforeShowDay"),v=this._get(a,"showOtherMonths"),H=this._get(a,"selectOtherMonths");this._get(a,"calculateWeek");for(var L=this._getDefaultDate(a),I="",C=0;C1)switch(D){case 0:x+=" ui-datepicker-group-first";t=" ui-corner-"+(c?"right":"left");break;case i[1]- +1:x+=" ui-datepicker-group-last";t=" ui-corner-"+(c?"left":"right");break;default:x+=" ui-datepicker-group-middle";t="";break}x+='">'}x+='
    '+(/all|left/.test(t)&&C==0?c?f:n:"")+(/all|right/.test(t)&&C==0?c?n:f:"")+this._generateMonthYearHeader(a,g,m,k,o,C>0||D>0,z,w)+'
    ';var A=j?'":"";for(t=0;t<7;t++){var q= +(t+h)%7;A+="=5?' class="ui-datepicker-week-end"':"")+'>'+s[q]+""}x+=A+"";A=this._getDaysInMonth(m,g);if(m==a.selectedYear&&g==a.selectedMonth)a.selectedDay=Math.min(a.selectedDay,A);t=(this._getFirstDayOfMonth(m,g)-h+7)%7;A=l?6:Math.ceil((t+A)/7);q=this._daylightSavingAdjust(new Date(m,g,1-t));for(var O=0;O";var P=!j?"":'";for(t=0;t<7;t++){var F= +p?p.apply(a.input?a.input[0]:null,[q]):[true,""],B=q.getMonth()!=g,J=B&&!H||!F[0]||k&&qo;P+='";q.setDate(q.getDate()+1);q=this._daylightSavingAdjust(q)}x+= +P+""}g++;if(g>11){g=0;m++}x+="
    '+this._get(a,"weekHeader")+"
    '+this._get(a,"calculateWeek")(q)+""+(B&&!v?" ":J?''+q.getDate()+"":''+q.getDate()+"")+"
    "+(l?""+(i[0]>0&&D==i[1]-1?'
    ':""):"");M+=x}I+=M}I+=e+(d.browser.msie&&parseInt(d.browser.version,10)<7&&!a.inline?'':"");a._keyEvent=false;return I},_generateMonthYearHeader:function(a,b,c,e,f,h,i,g){var j=this._get(a,"changeMonth"),l=this._get(a,"changeYear"),u=this._get(a,"showMonthAfterYear"),k='
    ', +o="";if(h||!j)o+=''+i[b]+"";else{i=e&&e.getFullYear()==c;var m=f&&f.getFullYear()==c;o+='"}u||(k+=o+(h||!(j&& +l)?" ":""));a.yearshtml="";if(h||!l)k+=''+c+"";else{g=this._get(a,"yearRange").split(":");var r=(new Date).getFullYear();i=function(s){s=s.match(/c[+-].*/)?c+parseInt(s.substring(1),10):s.match(/[+-].*/)?r+parseInt(s,10):parseInt(s,10);return isNaN(s)?r:s};b=i(g[0]);g=Math.max(b,i(g[1]||""));b=e?Math.max(b,e.getFullYear()):b;g=f?Math.min(g,f.getFullYear()):g;for(a.yearshtml+='";if(d.browser.mozilla)k+='";else{k+=a.yearshtml;a.yearshtml=null}}k+=this._get(a,"yearSuffix");if(u)k+=(h||!(j&&l)?" ":"")+o;k+="
    ";return k},_adjustInstDate:function(a,b,c){var e= +a.drawYear+(c=="Y"?b:0),f=a.drawMonth+(c=="M"?b:0);b=Math.min(a.selectedDay,this._getDaysInMonth(e,f))+(c=="D"?b:0);e=this._restrictMinMax(a,this._daylightSavingAdjust(new Date(e,f,b)));a.selectedDay=e.getDate();a.drawMonth=a.selectedMonth=e.getMonth();a.drawYear=a.selectedYear=e.getFullYear();if(c=="M"||c=="Y")this._notifyChange(a)},_restrictMinMax:function(a,b){var c=this._getMinMaxDate(a,"min");a=this._getMinMaxDate(a,"max");b=c&&ba?a:b},_notifyChange:function(a){var b=this._get(a, +"onChangeMonthYear");if(b)b.apply(a.input?a.input[0]:null,[a.selectedYear,a.selectedMonth+1,a])},_getNumberOfMonths:function(a){a=this._get(a,"numberOfMonths");return a==null?[1,1]:typeof a=="number"?[1,a]:a},_getMinMaxDate:function(a,b){return this._determineDate(a,this._get(a,b+"Date"),null)},_getDaysInMonth:function(a,b){return 32-(new Date(a,b,32)).getDate()},_getFirstDayOfMonth:function(a,b){return(new Date(a,b,1)).getDay()},_canAdjustMonth:function(a,b,c,e){var f=this._getNumberOfMonths(a); +c=this._daylightSavingAdjust(new Date(c,e+(b<0?b:f[0]*f[1]),1));b<0&&c.setDate(this._getDaysInMonth(c.getFullYear(),c.getMonth()));return this._isInRange(a,c)},_isInRange:function(a,b){var c=this._getMinMaxDate(a,"min");a=this._getMinMaxDate(a,"max");return(!c||b.getTime()>=c.getTime())&&(!a||b.getTime()<=a.getTime())},_getFormatConfig:function(a){var b=this._get(a,"shortYearCutoff");b=typeof b!="string"?b:(new Date).getFullYear()%100+parseInt(b,10);return{shortYearCutoff:b,dayNamesShort:this._get(a, +"dayNamesShort"),dayNames:this._get(a,"dayNames"),monthNamesShort:this._get(a,"monthNamesShort"),monthNames:this._get(a,"monthNames")}},_formatDate:function(a,b,c,e){if(!b){a.currentDay=a.selectedDay;a.currentMonth=a.selectedMonth;a.currentYear=a.selectedYear}b=b?typeof b=="object"?b:this._daylightSavingAdjust(new Date(e,c,b)):this._daylightSavingAdjust(new Date(a.currentYear,a.currentMonth,a.currentDay));return this.formatDate(this._get(a,"dateFormat"),b,this._getFormatConfig(a))}});d.fn.datepicker= +function(a){if(!d.datepicker.initialized){d(document).mousedown(d.datepicker._checkExternalClick).find("body").append(d.datepicker.dpDiv);d.datepicker.initialized=true}var b=Array.prototype.slice.call(arguments,1);if(typeof a=="string"&&(a=="isDisabled"||a=="getDate"||a=="widget"))return d.datepicker["_"+a+"Datepicker"].apply(d.datepicker,[this[0]].concat(b));if(a=="option"&&arguments.length==2&&typeof arguments[1]=="string")return d.datepicker["_"+a+"Datepicker"].apply(d.datepicker,[this[0]].concat(b)); +return this.each(function(){typeof a=="string"?d.datepicker["_"+a+"Datepicker"].apply(d.datepicker,[this].concat(b)):d.datepicker._attachDatepicker(this,a)})};d.datepicker=new K;d.datepicker.initialized=false;d.datepicker.uuid=(new Date).getTime();d.datepicker.version="1.8.7";window["DP_jQuery_"+y]=d})(jQuery); +;/* + * jQuery UI Progressbar 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Progressbar + * + * Depends: + * jquery.ui.core.js + * jquery.ui.widget.js + */ +(function(b,d){b.widget("ui.progressbar",{options:{value:0,max:100},min:0,_create:function(){this.element.addClass("ui-progressbar ui-widget ui-widget-content ui-corner-all").attr({role:"progressbar","aria-valuemin":this.min,"aria-valuemax":this.options.max,"aria-valuenow":this._value()});this.valueDiv=b("
    ").appendTo(this.element);this.oldValue=this._value();this._refreshValue()},destroy:function(){this.element.removeClass("ui-progressbar ui-widget ui-widget-content ui-corner-all").removeAttr("role").removeAttr("aria-valuemin").removeAttr("aria-valuemax").removeAttr("aria-valuenow"); +this.valueDiv.remove();b.Widget.prototype.destroy.apply(this,arguments)},value:function(a){if(a===d)return this._value();this._setOption("value",a);return this},_setOption:function(a,c){if(a==="value"){this.options.value=c;this._refreshValue();this._value()===this.options.max&&this._trigger("complete")}b.Widget.prototype._setOption.apply(this,arguments)},_value:function(){var a=this.options.value;if(typeof a!=="number")a=0;return Math.min(this.options.max,Math.max(this.min,a))},_percentage:function(){return 100* +this._value()/this.options.max},_refreshValue:function(){var a=this.value(),c=this._percentage();if(this.oldValue!==a){this.oldValue=a;this._trigger("change")}this.valueDiv.toggleClass("ui-corner-right",a===this.options.max).width(c.toFixed(0)+"%");this.element.attr("aria-valuenow",a)}});b.extend(b.ui.progressbar,{version:"1.8.7"})})(jQuery); +;/* + * jQuery UI Effects 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Effects/ + */ +jQuery.effects||function(f,j){function n(c){var a;if(c&&c.constructor==Array&&c.length==3)return c;if(a=/rgb\(\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*\)/.exec(c))return[parseInt(a[1],10),parseInt(a[2],10),parseInt(a[3],10)];if(a=/rgb\(\s*([0-9]+(?:\.[0-9]+)?)\%\s*,\s*([0-9]+(?:\.[0-9]+)?)\%\s*,\s*([0-9]+(?:\.[0-9]+)?)\%\s*\)/.exec(c))return[parseFloat(a[1])*2.55,parseFloat(a[2])*2.55,parseFloat(a[3])*2.55];if(a=/#([a-fA-F0-9]{2})([a-fA-F0-9]{2})([a-fA-F0-9]{2})/.exec(c))return[parseInt(a[1], +16),parseInt(a[2],16),parseInt(a[3],16)];if(a=/#([a-fA-F0-9])([a-fA-F0-9])([a-fA-F0-9])/.exec(c))return[parseInt(a[1]+a[1],16),parseInt(a[2]+a[2],16),parseInt(a[3]+a[3],16)];if(/rgba\(0, 0, 0, 0\)/.exec(c))return o.transparent;return o[f.trim(c).toLowerCase()]}function s(c,a){var b;do{b=f.curCSS(c,a);if(b!=""&&b!="transparent"||f.nodeName(c,"body"))break;a="backgroundColor"}while(c=c.parentNode);return n(b)}function p(){var c=document.defaultView?document.defaultView.getComputedStyle(this,null):this.currentStyle, +a={},b,d;if(c&&c.length&&c[0]&&c[c[0]])for(var e=c.length;e--;){b=c[e];if(typeof c[b]=="string"){d=b.replace(/\-(\w)/g,function(g,h){return h.toUpperCase()});a[d]=c[b]}}else for(b in c)if(typeof c[b]==="string")a[b]=c[b];return a}function q(c){var a,b;for(a in c){b=c[a];if(b==null||f.isFunction(b)||a in t||/scrollbar/.test(a)||!/color/i.test(a)&&isNaN(parseFloat(b)))delete c[a]}return c}function u(c,a){var b={_:0},d;for(d in a)if(c[d]!=a[d])b[d]=a[d];return b}function k(c,a,b,d){if(typeof c=="object"){d= +a;b=null;a=c;c=a.effect}if(f.isFunction(a)){d=a;b=null;a={}}if(typeof a=="number"||f.fx.speeds[a]){d=b;b=a;a={}}if(f.isFunction(b)){d=b;b=null}a=a||{};b=b||a.duration;b=f.fx.off?0:typeof b=="number"?b:b in f.fx.speeds?f.fx.speeds[b]:f.fx.speeds._default;d=d||a.complete;return[c,a,b,d]}function m(c){if(!c||typeof c==="number"||f.fx.speeds[c])return true;if(typeof c==="string"&&!f.effects[c])return true;return false}f.effects={};f.each(["backgroundColor","borderBottomColor","borderLeftColor","borderRightColor", +"borderTopColor","borderColor","color","outlineColor"],function(c,a){f.fx.step[a]=function(b){if(!b.colorInit){b.start=s(b.elem,a);b.end=n(b.end);b.colorInit=true}b.elem.style[a]="rgb("+Math.max(Math.min(parseInt(b.pos*(b.end[0]-b.start[0])+b.start[0],10),255),0)+","+Math.max(Math.min(parseInt(b.pos*(b.end[1]-b.start[1])+b.start[1],10),255),0)+","+Math.max(Math.min(parseInt(b.pos*(b.end[2]-b.start[2])+b.start[2],10),255),0)+")"}});var o={aqua:[0,255,255],azure:[240,255,255],beige:[245,245,220],black:[0, +0,0],blue:[0,0,255],brown:[165,42,42],cyan:[0,255,255],darkblue:[0,0,139],darkcyan:[0,139,139],darkgrey:[169,169,169],darkgreen:[0,100,0],darkkhaki:[189,183,107],darkmagenta:[139,0,139],darkolivegreen:[85,107,47],darkorange:[255,140,0],darkorchid:[153,50,204],darkred:[139,0,0],darksalmon:[233,150,122],darkviolet:[148,0,211],fuchsia:[255,0,255],gold:[255,215,0],green:[0,128,0],indigo:[75,0,130],khaki:[240,230,140],lightblue:[173,216,230],lightcyan:[224,255,255],lightgreen:[144,238,144],lightgrey:[211, +211,211],lightpink:[255,182,193],lightyellow:[255,255,224],lime:[0,255,0],magenta:[255,0,255],maroon:[128,0,0],navy:[0,0,128],olive:[128,128,0],orange:[255,165,0],pink:[255,192,203],purple:[128,0,128],violet:[128,0,128],red:[255,0,0],silver:[192,192,192],white:[255,255,255],yellow:[255,255,0],transparent:[255,255,255]},r=["add","remove","toggle"],t={border:1,borderBottom:1,borderColor:1,borderLeft:1,borderRight:1,borderTop:1,borderWidth:1,margin:1,padding:1};f.effects.animateClass=function(c,a,b, +d){if(f.isFunction(b)){d=b;b=null}return this.each(function(){f.queue(this,"fx",function(){var e=f(this),g=e.attr("style")||" ",h=q(p.call(this)),l,v=e.attr("className");f.each(r,function(w,i){c[i]&&e[i+"Class"](c[i])});l=q(p.call(this));e.attr("className",v);e.animate(u(h,l),a,b,function(){f.each(r,function(w,i){c[i]&&e[i+"Class"](c[i])});if(typeof e.attr("style")=="object"){e.attr("style").cssText="";e.attr("style").cssText=g}else e.attr("style",g);d&&d.apply(this,arguments)});h=f.queue(this);l= +h.splice(h.length-1,1)[0];h.splice(1,0,l);f.dequeue(this)})})};f.fn.extend({_addClass:f.fn.addClass,addClass:function(c,a,b,d){return a?f.effects.animateClass.apply(this,[{add:c},a,b,d]):this._addClass(c)},_removeClass:f.fn.removeClass,removeClass:function(c,a,b,d){return a?f.effects.animateClass.apply(this,[{remove:c},a,b,d]):this._removeClass(c)},_toggleClass:f.fn.toggleClass,toggleClass:function(c,a,b,d,e){return typeof a=="boolean"||a===j?b?f.effects.animateClass.apply(this,[a?{add:c}:{remove:c}, +b,d,e]):this._toggleClass(c,a):f.effects.animateClass.apply(this,[{toggle:c},a,b,d])},switchClass:function(c,a,b,d,e){return f.effects.animateClass.apply(this,[{add:a,remove:c},b,d,e])}});f.extend(f.effects,{version:"1.8.7",save:function(c,a){for(var b=0;b").addClass("ui-effects-wrapper").css({fontSize:"100%", +background:"transparent",border:"none",margin:0,padding:0});c.wrap(b);b=c.parent();if(c.css("position")=="static"){b.css({position:"relative"});c.css({position:"relative"})}else{f.extend(a,{position:c.css("position"),zIndex:c.css("z-index")});f.each(["top","left","bottom","right"],function(d,e){a[e]=c.css(e);if(isNaN(parseInt(a[e],10)))a[e]="auto"});c.css({position:"relative",top:0,left:0})}return b.css(a).show()},removeWrapper:function(c){if(c.parent().is(".ui-effects-wrapper"))return c.parent().replaceWith(c); +return c},setTransition:function(c,a,b,d){d=d||{};f.each(a,function(e,g){unit=c.cssUnit(g);if(unit[0]>0)d[g]=unit[0]*b+unit[1]});return d}});f.fn.extend({effect:function(c){var a=k.apply(this,arguments),b={options:a[1],duration:a[2],callback:a[3]};a=b.options.mode;var d=f.effects[c];if(f.fx.off||!d)return a?this[a](b.duration,b.callback):this.each(function(){b.callback&&b.callback.call(this)});return d.call(this,b)},_show:f.fn.show,show:function(c){if(m(c))return this._show.apply(this,arguments); +else{var a=k.apply(this,arguments);a[1].mode="show";return this.effect.apply(this,a)}},_hide:f.fn.hide,hide:function(c){if(m(c))return this._hide.apply(this,arguments);else{var a=k.apply(this,arguments);a[1].mode="hide";return this.effect.apply(this,a)}},__toggle:f.fn.toggle,toggle:function(c){if(m(c)||typeof c==="boolean"||f.isFunction(c))return this.__toggle.apply(this,arguments);else{var a=k.apply(this,arguments);a[1].mode="toggle";return this.effect.apply(this,a)}},cssUnit:function(c){var a=this.css(c), +b=[];f.each(["em","px","%","pt"],function(d,e){if(a.indexOf(e)>0)b=[parseFloat(a),e]});return b}});f.easing.jswing=f.easing.swing;f.extend(f.easing,{def:"easeOutQuad",swing:function(c,a,b,d,e){return f.easing[f.easing.def](c,a,b,d,e)},easeInQuad:function(c,a,b,d,e){return d*(a/=e)*a+b},easeOutQuad:function(c,a,b,d,e){return-d*(a/=e)*(a-2)+b},easeInOutQuad:function(c,a,b,d,e){if((a/=e/2)<1)return d/2*a*a+b;return-d/2*(--a*(a-2)-1)+b},easeInCubic:function(c,a,b,d,e){return d*(a/=e)*a*a+b},easeOutCubic:function(c, +a,b,d,e){return d*((a=a/e-1)*a*a+1)+b},easeInOutCubic:function(c,a,b,d,e){if((a/=e/2)<1)return d/2*a*a*a+b;return d/2*((a-=2)*a*a+2)+b},easeInQuart:function(c,a,b,d,e){return d*(a/=e)*a*a*a+b},easeOutQuart:function(c,a,b,d,e){return-d*((a=a/e-1)*a*a*a-1)+b},easeInOutQuart:function(c,a,b,d,e){if((a/=e/2)<1)return d/2*a*a*a*a+b;return-d/2*((a-=2)*a*a*a-2)+b},easeInQuint:function(c,a,b,d,e){return d*(a/=e)*a*a*a*a+b},easeOutQuint:function(c,a,b,d,e){return d*((a=a/e-1)*a*a*a*a+1)+b},easeInOutQuint:function(c, +a,b,d,e){if((a/=e/2)<1)return d/2*a*a*a*a*a+b;return d/2*((a-=2)*a*a*a*a+2)+b},easeInSine:function(c,a,b,d,e){return-d*Math.cos(a/e*(Math.PI/2))+d+b},easeOutSine:function(c,a,b,d,e){return d*Math.sin(a/e*(Math.PI/2))+b},easeInOutSine:function(c,a,b,d,e){return-d/2*(Math.cos(Math.PI*a/e)-1)+b},easeInExpo:function(c,a,b,d,e){return a==0?b:d*Math.pow(2,10*(a/e-1))+b},easeOutExpo:function(c,a,b,d,e){return a==e?b+d:d*(-Math.pow(2,-10*a/e)+1)+b},easeInOutExpo:function(c,a,b,d,e){if(a==0)return b;if(a== +e)return b+d;if((a/=e/2)<1)return d/2*Math.pow(2,10*(a-1))+b;return d/2*(-Math.pow(2,-10*--a)+2)+b},easeInCirc:function(c,a,b,d,e){return-d*(Math.sqrt(1-(a/=e)*a)-1)+b},easeOutCirc:function(c,a,b,d,e){return d*Math.sqrt(1-(a=a/e-1)*a)+b},easeInOutCirc:function(c,a,b,d,e){if((a/=e/2)<1)return-d/2*(Math.sqrt(1-a*a)-1)+b;return d/2*(Math.sqrt(1-(a-=2)*a)+1)+b},easeInElastic:function(c,a,b,d,e){c=1.70158;var g=0,h=d;if(a==0)return b;if((a/=e)==1)return b+d;g||(g=e*0.3);if(h").css({position:"absolute",visibility:"visible",left:-f*(h/d),top:-e*(i/c)}).parent().addClass("ui-effects-explode").css({position:"absolute",overflow:"hidden",width:h/d,height:i/c,left:g.left+f*(h/d)+(a.options.mode=="show"?(f-Math.floor(d/2))*(h/d):0),top:g.top+e*(i/c)+(a.options.mode=="show"?(e-Math.floor(c/2))*(i/c):0),opacity:a.options.mode=="show"?0:1}).animate({left:g.left+f*(h/d)+(a.options.mode=="show"?0:(f-Math.floor(d/2))*(h/d)),top:g.top+ +e*(i/c)+(a.options.mode=="show"?0:(e-Math.floor(c/2))*(i/c)),opacity:a.options.mode=="show"?1:0},a.duration||500);setTimeout(function(){a.options.mode=="show"?b.css({visibility:"visible"}):b.css({visibility:"visible"}).hide();a.callback&&a.callback.apply(b[0]);b.dequeue();j("div.ui-effects-explode").remove()},a.duration||500)})}})(jQuery); +;/* + * jQuery UI Effects Fade 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Effects/Fade + * + * Depends: + * jquery.effects.core.js + */ +(function(b){b.effects.fade=function(a){return this.queue(function(){var c=b(this),d=b.effects.setMode(c,a.options.mode||"hide");c.animate({opacity:d},{queue:false,duration:a.duration,easing:a.options.easing,complete:function(){a.callback&&a.callback.apply(this,arguments);c.dequeue()}})})}})(jQuery); +;/* + * jQuery UI Effects Fold 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Effects/Fold + * + * Depends: + * jquery.effects.core.js + */ +(function(c){c.effects.fold=function(a){return this.queue(function(){var b=c(this),j=["position","top","left"],d=c.effects.setMode(b,a.options.mode||"hide"),g=a.options.size||15,h=!!a.options.horizFirst,k=a.duration?a.duration/2:c.fx.speeds._default/2;c.effects.save(b,j);b.show();var e=c.effects.createWrapper(b).css({overflow:"hidden"}),f=d=="show"!=h,l=f?["width","height"]:["height","width"];f=f?[e.width(),e.height()]:[e.height(),e.width()];var i=/([0-9]+)%/.exec(g);if(i)g=parseInt(i[1],10)/100* +f[d=="hide"?0:1];if(d=="show")e.css(h?{height:0,width:g}:{height:g,width:0});h={};i={};h[l[0]]=d=="show"?f[0]:g;i[l[1]]=d=="show"?f[1]:0;e.animate(h,k,a.options.easing).animate(i,k,a.options.easing,function(){d=="hide"&&b.hide();c.effects.restore(b,j);c.effects.removeWrapper(b);a.callback&&a.callback.apply(b[0],arguments);b.dequeue()})})}})(jQuery); +;/* + * jQuery UI Effects Highlight 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Effects/Highlight + * + * Depends: + * jquery.effects.core.js + */ +(function(b){b.effects.highlight=function(c){return this.queue(function(){var a=b(this),e=["backgroundImage","backgroundColor","opacity"],d=b.effects.setMode(a,c.options.mode||"show"),f={backgroundColor:a.css("backgroundColor")};if(d=="hide")f.opacity=0;b.effects.save(a,e);a.show().css({backgroundImage:"none",backgroundColor:c.options.color||"#ffff99"}).animate(f,{queue:false,duration:c.duration,easing:c.options.easing,complete:function(){d=="hide"&&a.hide();b.effects.restore(a,e);d=="show"&&!b.support.opacity&& +this.style.removeAttribute("filter");c.callback&&c.callback.apply(this,arguments);a.dequeue()}})})}})(jQuery); +;/* + * jQuery UI Effects Pulsate 1.8.7 + * + * Copyright 2010, AUTHORS.txt (http://jqueryui.com/about) + * Dual licensed under the MIT or GPL Version 2 licenses. + * http://jquery.org/license + * + * http://docs.jquery.com/UI/Effects/Pulsate + * + * Depends: + * jquery.effects.core.js + */ +(function(d){d.effects.pulsate=function(a){return this.queue(function(){var b=d(this),c=d.effects.setMode(b,a.options.mode||"show");times=(a.options.times||5)*2-1;duration=a.duration?a.duration/2:d.fx.speeds._default/2;isVisible=b.is(":visible");animateTo=0;if(!isVisible){b.css("opacity",0).show();animateTo=1}if(c=="hide"&&isVisible||c=="show"&&!isVisible)times--;for(c=0;c').appendTo(document.body).addClass(a.options.className).css({top:d.top,left:d.left,height:b.innerHeight(),width:b.innerWidth(),position:"absolute"}).animate(c,a.duration,a.options.easing,function(){f.remove();a.callback&&a.callback.apply(b[0],arguments); +b.dequeue()})})}})(jQuery); +; \ No newline at end of file diff --git a/sources/www/jquery/jquery.autocomplete-1.1.js b/sources/www/jquery/jquery.autocomplete-1.1.js new file mode 100644 index 0000000..a0daba2 --- /dev/null +++ b/sources/www/jquery/jquery.autocomplete-1.1.js @@ -0,0 +1,839 @@ +/* + * jQuery Autocomplete plugin 1.1 + * + * Copyright (c) 2009 Jörn Zaefferer + * + * Dual licensed under the MIT and GPL licenses: + * http://www.opensource.org/licenses/mit-license.php + * http://www.gnu.org/licenses/gpl.html + * + * Revision: $Id: jquery.autocomplete.js 15 2009-08-22 10:30:27Z joern.zaefferer $ + */ + +/* + * Changes for myTinyTodo, www.mytinytodo.net + * Copyright (c) 2010 Max Pozdeev + * Dual licensed under the MIT and GPL licenses + */ + +;(function($) { + +$.fn.extend({ + autocomplete: function(urlOrData, options) { + var isUrl = typeof urlOrData == "string"; + var isFunc = typeof urlOrData == "function"; + options = $.extend({}, $.Autocompleter.defaults, { + url: isUrl ? urlOrData : null, + data: !isUrl && !isFunc ? urlOrData : null, + func: isFunc ? urlOrData : null, + delay: isUrl ? $.Autocompleter.defaults.delay : 10, + max: options && !options.scroll ? 10 : 150 + }, options); + + // if highlight is set to false, replace it with a do-nothing function + options.highlight = options.highlight || function(value) { return value; }; + + // if the formatMatch option is not specified, then use formatItem for backwards compatibility + options.formatMatch = options.formatMatch || options.formatItem; + + return this.each(function() { + new $.Autocompleter(this, options); + }); + }, + result: function(handler) { + return this.bind("result", handler); + }, + search: function(handler) { + return this.trigger("search", [handler]); + }, + flushCache: function() { + return this.trigger("flushCache"); + }, + setOptions: function(options){ + return this.trigger("setOptions", [options]); + }, + unautocomplete: function() { + return this.trigger("unautocomplete"); + } +}); + +$.Autocompleter = function(input, options) { + + var KEY = { + UP: 38, + DOWN: 40, + DEL: 46, + TAB: 9, + RETURN: 13, + ESC: 27, + COMMA: 188, + PAGEUP: 33, + PAGEDOWN: 34, + BACKSPACE: 8 + }; + + // Create $ object for input element + var $input = $(input).attr("autocomplete", "off").addClass(options.inputClass); + + var timeout; + var previousValue = ""; + var cache = $.Autocompleter.Cache(options); + var hasFocus = 0; + var lastKeyPressCode; + var config = { + mouseDownOnSelect: false + }; + var select = $.Autocompleter.Select(options, input, selectCurrent, config); + + var blockSubmit; + + // prevent form submit in opera when selecting with return key + $.browser.opera && $(input.form).bind("submit.autocomplete", function() { + if (blockSubmit) { + blockSubmit = false; + return false; + } + }); + + // only opera doesn't trigger keydown multiple times while pressed, others don't work with keypress at all + $input.bind(($.browser.opera ? "keypress" : "keydown") + ".autocomplete", function(event) { + // a keypress means the input has focus + // avoids issue where input had focus before the autocomplete was applied + hasFocus = 1; + // track last key pressed + lastKeyPressCode = event.keyCode; + switch(event.keyCode) { + + case KEY.UP: + event.preventDefault(); + if ( select.visible() ) { + select.prev(); + } else { + onChange(0, true); + } + break; + + case KEY.DOWN: + event.preventDefault(); + if ( select.visible() ) { + select.next(); + } else { + onChange(0, true); + } + break; + + case KEY.PAGEUP: + event.preventDefault(); + if ( select.visible() ) { + select.pageUp(); + } else { + onChange(0, true); + } + break; + + case KEY.PAGEDOWN: + event.preventDefault(); + if ( select.visible() ) { + select.pageDown(); + } else { + onChange(0, true); + } + break; + + // matches also semicolon + case options.multiple && $.trim(options.multipleSeparator) == "," && KEY.COMMA: + case KEY.TAB: + case KEY.RETURN: + if( selectCurrent() ) { + // stop default to prevent a form submit, Opera needs special handling + event.preventDefault(); + blockSubmit = true; + return false; + } + break; + + case KEY.ESC: + select.hide(); + break; + + default: + clearTimeout(timeout); + timeout = setTimeout(onChange, options.delay); + break; + } + }).focus(function(){ + // track whether the field has focus, we shouldn't process any + // results if the field no longer has focus + hasFocus++; + }).blur(function() { + hasFocus = 0; + if (!config.mouseDownOnSelect) { + hideResults(); + } + }).click(function() { + // show select when clicking in a focused field + if ( hasFocus++ > 1 && !select.visible() ) { + onChange(0, true); + } + }).bind("search", function() { + // TODO why not just specifying both arguments? + var fn = (arguments.length > 1) ? arguments[1] : null; + function findValueCallback(q, data) { + var result; + if( data && data.length ) { + for (var i=0; i < data.length; i++) { + if( data[i].result.toLowerCase() == q.toLowerCase() ) { + result = data[i]; + break; + } + } + } + if( typeof fn == "function" ) fn(result); + else $input.trigger("result", result && [result.data, result.value]); + } + $.each(trimWords($input.val()), function(i, value) { + request(value, findValueCallback, findValueCallback); + }); + }).bind("flushCache", function() { + cache.flush(); + }).bind("setOptions", function() { + $.extend(options, arguments[1]); + // if we've updated the data, repopulate + if ( "data" in arguments[1] ) + cache.populate(); + }).bind("unautocomplete", function() { + select.unbind(); + $input.unbind(); + $(input.form).unbind(".autocomplete"); + }); + + + function selectCurrent() { + var selected = select.selected(); + if( !selected ) + return false; + + var v = selected.result; + previousValue = v; + + if ( options.multiple ) { + var words = trimWords($input.val()); + if ( words.length > 1 ) { + var seperator = options.multipleSeparator.length; + var cursorAt = $(input).selection().start; + var wordAt, progress = 0; + $.each(words, function(i, word) { + progress += word.length; + if (cursorAt <= progress) { + wordAt = i; + return false; + } + progress += seperator; + }); + words[wordAt] = v; + // TODO this should set the cursor to the right position, but it gets overriden somewhere + //$.Autocompleter.Selection(input, progress + seperator, progress + seperator); + v = words.join( options.multipleSeparator ); + } + v += options.multipleSeparator; + } + + $input.val(v); + hideResultsNow(); + $input.trigger("result", [selected.data, selected.value]); + return true; + } + + function onChange(crap, skipPrevCheck) { + if( lastKeyPressCode == KEY.DEL ) { + select.hide(); + return; + } + + var currentValue = $input.val(); + + if ( !skipPrevCheck && currentValue == previousValue ) + return; + + previousValue = currentValue; + + currentValue = lastWord(currentValue); + if ( currentValue.length >= options.minChars) { + $input.addClass(options.loadingClass); + if (!options.matchCase) + currentValue = currentValue.toLowerCase(); + request(currentValue, receiveData, hideResultsNow); + } else { + stopLoading(); + select.hide(); + } + }; + + function trimWords(value) { + if (!value) + return [""]; + if (!options.multiple) + return [$.trim(value)]; + return $.map(value.split(options.multipleSeparator), function(word) { + return $.trim(value).length ? $.trim(word) : null; + }); + } + + function lastWord(value) { + if ( !options.multiple ) + return value; + var words = trimWords(value); + if (words.length == 1) + return words[0]; + var cursorAt = $(input).selection().start; + if (cursorAt == value.length) { + words = trimWords(value) + } else { + words = trimWords(value.replace(value.substring(cursorAt), "")); + } + return words[words.length - 1]; + } + + // fills in the input box w/the first match (assumed to be the best match) + // q: the term entered + // sValue: the first matching result + function autoFill(q, sValue){ + // autofill in the complete box w/the first match as long as the user hasn't entered in more data + // if the last user key pressed was backspace, don't autofill + if( options.autoFill && (lastWord($input.val()).toLowerCase() == q.toLowerCase()) && lastKeyPressCode != KEY.BACKSPACE ) { + // fill in the value (keep the case the user has typed) + $input.val($input.val() + sValue.substring(lastWord(previousValue).length)); + // select the portion of the value not typed by the user (so the next character will erase) + $(input).selection(previousValue.length, previousValue.length + sValue.length); + } + }; + + function hideResults() { + clearTimeout(timeout); + timeout = setTimeout(hideResultsNow, 200); + }; + + function hideResultsNow() { + var wasVisible = select.visible(); + select.hide(); + clearTimeout(timeout); + stopLoading(); + if (options.mustMatch) { + // call search and run callback + $input.search( + function (result){ + // if no value found, clear the input box + if( !result ) { + if (options.multiple) { + var words = trimWords($input.val()).slice(0, -1); + $input.val( words.join(options.multipleSeparator) + (words.length ? options.multipleSeparator : "") ); + } + else { + $input.val( "" ); + $input.trigger("result", null); + } + } + } + ); + } + }; + + function receiveData(q, data) { + if ( data && data.length && hasFocus ) { + stopLoading(); + select.display(data, q); + autoFill(q, data[0].value); + select.show(); + } else { + hideResultsNow(); + } + }; + + function request(term, success, failure) { + if (!options.matchCase) + term = term.toLowerCase(); + var data = cache.load(term); + // recieve the cached data + if (data && data.length) { + success(term, data); + } + // if function was supplied + else if(options.func) + { + var extraParams = { + timestamp: +new Date() + }; + $.each(options.extraParams, function(key, param) { + extraParams[key] = typeof param == "function" ? param() : param; + }); + + options.func({ + data: $.extend({ + q: lastWord(term), + limit: options.max + }, extraParams)}, + function(data){ + var parsed = options.parse && options.parse(data) || parse(data); + cache.add(term, parsed) + success(term, parsed); + } + ); + } + // if an AJAX url has been supplied, try loading the data now + else if( (typeof options.url == "string") && (options.url.length > 0) ){ + + var extraParams = { + timestamp: +new Date() + }; + $.each(options.extraParams, function(key, param) { + extraParams[key] = typeof param == "function" ? param() : param; + }); + + $.ajax({ + // try to leverage ajaxQueue plugin to abort previous requests + mode: "abort", + // limit abortion to this input + port: "autocomplete" + input.name, + dataType: options.dataType, + url: options.url, + data: $.extend({ + q: lastWord(term), + limit: options.max + }, extraParams), + success: function(data) { + var parsed = options.parse && options.parse(data) || parse(data); + cache.add(term, parsed); + success(term, parsed); + } + }); + } else { + // if we have a failure, we need to empty the list -- this prevents the the [TAB] key from selecting the last successful match + select.emptyList(); + failure(term); + } + }; + + function parse(data) { + var parsed = []; + var rows = data.split("\n"); + for (var i=0; i < rows.length; i++) { + var row = $.trim(rows[i]); + if (row) { + row = row.split("|"); + parsed[parsed.length] = { + data: row, + value: row[0], + result: options.formatResult && options.formatResult(row, row[0]) || row[0] + }; + } + } + return parsed; + }; + + function stopLoading() { + $input.removeClass(options.loadingClass); + }; + +}; + +$.Autocompleter.defaults = { + inputClass: "ac_input", + resultsClass: "ac_results", + loadingClass: "ac_loading", + minChars: 1, + delay: 400, + matchCase: false, + matchSubset: true, + matchContains: false, + cacheLength: 10, + max: 100, + mustMatch: false, + extraParams: {}, + selectFirst: true, + formatItem: function(row) { return row[0]; }, + formatMatch: null, + autoFill: false, + width: 0, + multiple: false, + multipleSeparator: ", ", + highlight: function(value, term) { + return value.replace(new RegExp("(?![^&;]+;)(?!<[^<>]*)(" + term.replace(/([\^\$\(\)\[\]\{\}\*\.\+\?\|\\])/gi, "\\$1") + ")(?![^<>]*>)(?![^&;]+;)", "gi"), "$1"); + }, + scroll: true, + scrollHeight: 180 +}; + +$.Autocompleter.Cache = function(options) { + + var data = {}; + var length = 0; + + function matchSubset(s, sub) { + if (!options.matchCase) + s = s.toLowerCase(); + var i = s.indexOf(sub); + if (options.matchContains == "word"){ + i = s.toLowerCase().search("\\b" + sub.toLowerCase()); + } + if (i == -1) return false; + return i == 0 || options.matchContains; + }; + + function add(q, value) { + if (length > options.cacheLength){ + flush(); + } + if (!data[q]){ + length++; + } + data[q] = value; + } + + function populate(){ + if( !options.data ) return false; + // track the matches + var stMatchSets = {}, + nullData = 0; + + // no url was specified, we need to adjust the cache length to make sure it fits the local data store + if( !options.url && !options.func ) options.cacheLength = 1; + + // track all options for minChars = 0 + stMatchSets[""] = []; + + // loop through the array and create a lookup structure + for ( var i = 0, ol = options.data.length; i < ol; i++ ) { + var rawValue = options.data[i]; + // if rawValue is a string, make an array otherwise just reference the array + rawValue = (typeof rawValue == "string") ? [rawValue] : rawValue; + + var value = options.formatMatch(rawValue, i+1, options.data.length); + if ( value === false ) + continue; + + var firstChar = value.charAt(0).toLowerCase(); + // if no lookup array for this character exists, look it up now + if( !stMatchSets[firstChar] ) + stMatchSets[firstChar] = []; + + // if the match is a string + var row = { + value: value, + data: rawValue, + result: options.formatResult && options.formatResult(rawValue) || value + }; + + // push the current match into the set list + stMatchSets[firstChar].push(row); + + // keep track of minChars zero items + if ( nullData++ < options.max ) { + stMatchSets[""].push(row); + } + }; + + // add the data items to the cache + $.each(stMatchSets, function(i, value) { + // increase the cache size + options.cacheLength++; + // add to the cache + add(i, value); + }); + } + + // populate any existing data + setTimeout(populate, 25); + + function flush(){ + data = {}; + length = 0; + } + + return { + flush: flush, + add: add, + populate: populate, + load: function(q) { + if (!options.cacheLength || !length) + return null; + /* + * if dealing w/local data and matchContains than we must make sure + * to loop through all the data collections looking for matches + */ + if( (!options.url && !options.func) && options.matchContains ){ + // track all matches + var csub = []; + // loop through all the data grids for matches + for( var k in data ){ + // don't search through the stMatchSets[""] (minChars: 0) cache + // this prevents duplicates + if( k.length > 0 ){ + var c = data[k]; + $.each(c, function(i, x) { + // if we've got a match, add it to the array + if (matchSubset(x.value, q)) { + csub.push(x); + } + }); + } + } + return csub; + } else + // if the exact item exists, use it + if (data[q]){ + return data[q]; + } else + if (options.matchSubset) { + for (var i = q.length - 1; i >= options.minChars; i--) { + var c = data[q.substr(0, i)]; + if (c) { + var csub = []; + $.each(c, function(i, x) { + if (matchSubset(x.value, q)) { + csub[csub.length] = x; + } + }); + return csub; + } + } + } + return null; + } + }; +}; + +$.Autocompleter.Select = function (options, input, select, config) { + var CLASSES = { + ACTIVE: "ac_over" + }; + + var listItems, + active = -1, + data, + term = "", + needsInit = true, + element, + list; + + // Create results + function init() { + if (!needsInit) + return; + element = $("
    ") + .hide() + .addClass(options.resultsClass) + .css("position", "absolute") + .appendTo(document.body); + + list = $("
      ").appendTo(element).mouseover( function(event) { + if(target(event).nodeName && target(event).nodeName.toUpperCase() == 'LI') { + active = $("li", list).removeClass(CLASSES.ACTIVE).index(target(event)); + $(target(event)).addClass(CLASSES.ACTIVE); + } + }).click(function(event) { + $(target(event)).addClass(CLASSES.ACTIVE); + select(); + // TODO provide option to avoid setting focus again after selection? useful for cleanup-on-focus + input.focus(); + return false; + }).mousedown(function() { + config.mouseDownOnSelect = true; + }).mouseup(function() { + config.mouseDownOnSelect = false; + }); + + if( options.width > 0 ) + element.css("width", options.width); + + needsInit = false; + } + + function target(event) { + var element = event.target; + while(element && element.tagName.toUpperCase() != "LI") + element = element.parentNode; + // more fun with IE, sometimes event.target is empty, just ignore it then + if(!element) + return []; + return element; + } + + function moveSelect(step) { + listItems.slice(active, active + 1).removeClass(CLASSES.ACTIVE); + movePosition(step); + var activeItem = listItems.slice(active, active + 1).addClass(CLASSES.ACTIVE); + if(options.scroll) { + var offset = 0; + listItems.slice(0, active).each(function() { + offset += this.offsetHeight; + }); + if((offset + activeItem[0].offsetHeight - list.scrollTop()) > list[0].clientHeight) { + list.scrollTop(offset + activeItem[0].offsetHeight - list.innerHeight()); + } else if(offset < list.scrollTop()) { + list.scrollTop(offset); + } + } + }; + + function movePosition(step) { + active += step; + if (active < 0) { + active = listItems.size() - 1; + } else if (active >= listItems.size()) { + active = 0; + } + } + + function limitNumberOfItems(available) { + return options.max && options.max < available + ? options.max + : available; + } + + function fillList() { + list.empty(); + var max = limitNumberOfItems(data.length); + for (var i=0; i < max; i++) { + if (!data[i]) + continue; + var formatted = options.formatItem(data[i].data, i+1, max, data[i].value, term); + if ( formatted === false ) + continue; + var li = $("
    • ").html( options.highlight(formatted, term) ).addClass(i%2 == 0 ? "ac_even" : "ac_odd").appendTo(list)[0]; + $.data(li, "ac_data", data[i]); + } + listItems = list.find("li"); + if ( options.selectFirst ) { + listItems.slice(0, 1).addClass(CLASSES.ACTIVE); + active = 0; + } + // apply bgiframe if available + if ( $.fn.bgiframe ) + list.bgiframe(); + } + + return { + display: function(d, q) { + init(); + data = d; + term = q; + fillList(); + }, + next: function() { + moveSelect(1); + }, + prev: function() { + moveSelect(-1); + }, + pageUp: function() { + if (active != 0 && active - 8 < 0) { + moveSelect( -active ); + } else { + moveSelect(-8); + } + }, + pageDown: function() { + if (active != listItems.size() - 1 && active + 8 > listItems.size()) { + moveSelect( listItems.size() - 1 - active ); + } else { + moveSelect(8); + } + }, + hide: function() { + element && element.hide(); + listItems && listItems.removeClass(CLASSES.ACTIVE); + active = -1; + }, + visible : function() { + return element && element.is(":visible"); + }, + current: function() { + return this.visible() && (listItems.filter("." + CLASSES.ACTIVE)[0] || options.selectFirst && listItems[0]); + }, + show: function() { + var offset = $(input).offset(); + element.css({ + width: typeof options.width == "string" || options.width > 0 ? options.width : $(input).width(), + top: offset.top + input.offsetHeight, + left: offset.left + }).show(); + if(options.scroll) { + list.scrollTop(0); + list.css({ + maxHeight: options.scrollHeight, + overflow: 'auto' + }); + + if($.browser.msie && typeof document.body.style.maxHeight === "undefined") { + var listHeight = 0; + listItems.each(function() { + listHeight += this.offsetHeight; + }); + var scrollbarsVisible = listHeight > options.scrollHeight; + list.css('height', scrollbarsVisible ? options.scrollHeight : listHeight ); + if (!scrollbarsVisible) { + // IE doesn't recalculate width when scrollbar disappears + listItems.width( list.width() - parseInt(listItems.css("padding-left")) - parseInt(listItems.css("padding-right")) ); + } + } + + } + }, + selected: function() { + var selected = listItems && listItems.filter("." + CLASSES.ACTIVE).removeClass(CLASSES.ACTIVE); + return selected && selected.length && $.data(selected[0], "ac_data"); + }, + emptyList: function (){ + list && list.empty(); + }, + unbind: function() { + element && element.remove(); + } + }; +}; + +$.fn.selection = function(start, end) { + if (start !== undefined) { + return this.each(function() { + if( this.createTextRange ){ + var selRange = this.createTextRange(); + if (end === undefined || start == end) { + selRange.move("character", start); + selRange.select(); + } else { + selRange.collapse(true); + selRange.moveStart("character", start); + selRange.moveEnd("character", end); + selRange.select(); + } + } else if( this.setSelectionRange ){ + this.setSelectionRange(start, end); + } else if( this.selectionStart ){ + this.selectionStart = start; + this.selectionEnd = end; + } + }); + } + var field = this[0]; + if ( field.createTextRange ) { + var range = document.selection.createRange(), + orig = field.value, + teststring = "<->", + textLength = range.text.length; + range.text = teststring; + var caretAt = field.value.indexOf(teststring); + field.value = orig; + this.selection(caretAt, caretAt + textLength); + return { + start: caretAt, + end: caretAt + textLength + } + } else if( field.selectionStart !== undefined ){ + return { + start: field.selectionStart, + end: field.selectionEnd + } + } +}; + +})(jQuery); \ No newline at end of file diff --git a/sources/www/lang/.htaccess b/sources/www/lang/.htaccess new file mode 100644 index 0000000..3418e55 --- /dev/null +++ b/sources/www/lang/.htaccess @@ -0,0 +1 @@ +deny from all \ No newline at end of file diff --git a/sources/www/lang/class.default.php b/sources/www/lang/class.default.php new file mode 100644 index 0000000..2c2e862 --- /dev/null +++ b/sources/www/lang/class.default.php @@ -0,0 +1,201 @@ + "Are you sure you want to delete the task?", + 'confirmLeave' => "There can be unsaved data. Do you really want to leave?", + 'actionNoteSave' => "save", + 'actionNoteCancel' => "cancel", + 'error' => "Some error occurred (click for details)", + 'denied' => "Access denied", + 'invalidpass' => "Wrong password", + 'tagfilter' => "Tag:", + 'addList' => "Create new list", + 'addListDefault' => "Todo", + 'renameList' => "Rename list", + 'deleteList' => "This will delete current list with all tasks in it.\\nAre you sure?", + 'clearCompleted' => "This will delete all completed tasks in the list.\\nAre you sure?", + 'settingsSaved' => "Settings saved. Reloading...", + ); + + private $default_inc = array + ( + 'My Tiny Todolist' => "My Tiny Todolist", + 'htab_newtask' => "New task", + 'htab_search' => "Search", + 'btn_add' => "Add", + 'btn_search' => "Search", + 'advanced_add' => "Advanced", + 'searching' => "Searching for", + 'tasks' => "Tasks", + 'taskdate_inline_created' => "created at %s", + 'taskdate_inline_completed' => "Completed at %s", + 'taskdate_inline_duedate' => "Due %s", + 'taskdate_created' => "Created", + 'taskdate_completed' => "Completed", + 'go_back' => "<< Back", + 'edit_task' => "Edit Task", + 'add_task' => "New Task", + 'priority' => "Priority", + 'task' => "Task", + 'note' => "Note", + 'tags' => "Tags", + 'save' => "Save", + 'cancel' => "Cancel", + 'password' => "Password", + 'btn_login' => "Login", + 'a_login' => "Login", + 'a_logout' => "Logout", + 'public_tasks' => "Public Tasks", + 'tagcloud' => "Tags", + 'tagfilter_cancel' => "cancel filter", + 'sortByHand' => "Sort by hand", + 'sortByPriority' => "Sort by priority", + 'sortByDueDate' => "Sort by due date", + 'sortByDateCreated' => "Sort by date created", + 'sortByDateModified' => "Sort by date modified", + 'due' => "Due", + 'daysago' => "%d days ago", + 'indays' => "in %d days", + 'months_short' => array("Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"), + 'months_long' => array("January","February","March","April","May","June","July","August","September","October","November","December"), + 'days_min' => array("Su","Mo","Tu","We","Th","Fr","Sa"), + 'days_long' => array("Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"), + 'today' => "today", + 'yesterday' => "yesterday", + 'tomorrow' => "tomorrow", + 'f_past' => "Overdue", + 'f_today' => "Today and tomorrow", + 'f_soon' => "Soon", + 'action_edit' => "Edit", + 'action_note' => "Edit Note", + 'action_delete' => "Delete", + 'action_priority' => "Priority", + 'action_move' => "Move to", + 'notes' => "Notes:", + 'notes_show' => "Show", + 'notes_hide' => "Hide", + 'list_new' => "New list", + 'list_rename' => "Rename list", + 'list_delete' => "Delete list", + 'list_publish' => "Publish list", + 'list_showcompleted' => "Show completed tasks", + 'list_clearcompleted' => "Clear completed tasks", + 'list_select' => "Select list", + 'list_export' => "Export", + 'list_export_csv' => "CSV", + 'list_export_ical' => "iCalendar", + 'list_rssfeed' => "RSS Feed", + 'alltags' => "All tags:", + 'alltags_show' => "Show all", + 'alltags_hide' => "Hide all", + 'a_settings' => "Settings", + 'rss_feed' => "RSS Feed", + 'feed_title' => "%s", + 'feed_completed_tasks' => "Completed tasks", + 'feed_modified_tasks' => "Modified tasks", + 'feed_new_tasks' => "New tasks", + 'alltasks' => "All tasks", + + /* Settings */ + 'set_header' => "Settings", + 'set_title' => "Title", + 'set_title_descr' => "(specify if you want to change default title)", + 'set_language' => "Language", + 'set_protection' => "Password protection", + 'set_enabled' => "Enabled", + 'set_disabled' => "Disabled", + 'set_newpass' => "New password", + 'set_newpass_descr' => "(leave blank if won't change current password)", + 'set_smartsyntax' => "Smart syntax", + 'set_smartsyntax_descr' => "(/priority/ task /tags/)", + 'set_timezone' => "Time zone", + 'set_autotag' => "Autotagging", + 'set_autotag_descr' => "(automatically adds tag of current tag filter to newly created task)", + 'set_sessions' => "Session handling mechanism", + 'set_sessions_php' => "PHP", + 'set_sessions_files' => "Files", + 'set_firstdayofweek' => "First day of week", + 'set_custom' => "Custom", + 'set_date' => "Date format", + 'set_date2' => "Short Date format", + 'set_shortdate' => "Short Date (current year)", + 'set_clock' => "Clock format", + 'set_12hour' => "12-hour", + 'set_24hour' => "24-hour", + 'set_submit' => "Submit changes", + 'set_cancel' => "Cancel", + 'set_showdate' => "Show task date in list", + ); + + var $js = array(); + var $inc = array(); + + function makeJS() + { + $a = array(); + foreach($this->default_js as $k=>$v) + { + if(isset($this->js[$k])) $v = $this->js[$k]; + + if(is_array($v)) { + $a[] = "$k: ". $v[0]; + } else { + $a[] = "$k: \"". str_replace('"','\\"',$v). "\""; + } + } + $t = array(); + foreach($this->get('days_min') as $v) { $t[] = '"'.str_replace('"','\\"',$v).'"'; } + $a[] = "daysMin: [". implode(',', $t). "]"; + $t = array(); + foreach($this->get('days_long') as $v) { $t[] = '"'.str_replace('"','\\"',$v).'"'; } + $a[] = "daysLong: [". implode(',', $t). "]"; + $t = array(); + foreach($this->get('months_long') as $v) { $t[] = '"'.str_replace('"','\\"',$v).'"'; } + $a[] = "monthsLong: [". implode(',', $t). "]"; + $a[] = $this->_2js('tags'); + $a[] = $this->_2js('tasks'); + $a[] = $this->_2js('f_past'); + $a[] = $this->_2js('f_today'); + $a[] = $this->_2js('f_soon'); + return "{\n". implode(",\n", $a). "\n}"; + } + + function _2js($v) + { + return "$v: \"". str_replace('"','\\"',$this->get($v)). "\""; + } + + function get($key) + { + if(isset($this->inc[$key])) return $this->inc[$key]; + if(isset($this->default_inc[$key])) return $this->default_inc[$key]; + return $key; + } + + function rtl() + { + return $this->rtl ? 1 : 0; + } + + public static function instance() + { + if (!isset(self::$instance)) { + //$c = __CLASS__; + $c = 'Lang'; + self::$instance = new $c; + } + return self::$instance; + } +} + +?> \ No newline at end of file diff --git a/sources/www/lang/de.php b/sources/www/lang/de.php new file mode 100644 index 0000000..5ed8cbc --- /dev/null +++ b/sources/www/lang/de.php @@ -0,0 +1,138 @@ + 'Willst Du die Aufgabe wirklich löschen?', + 'confirmLeave' => 'Einige Daten wurden noch nicht gespeichert. Willst du die Seite wirklich verlassen?', + 'actionNoteSave' => 'speichern', + 'actionNoteCancel' => 'abbrechen', + 'error' => 'Fehler aufgetreten (für Details klicken)', + 'denied' => 'Zugriff verweigert', + 'invalidpass' => 'Falsches Passwort', + 'tagfilter' => 'Schlagwort:', + 'addList' => 'Neue Liste anlegen', + 'renameList' => 'Liste umbenennen', + 'deleteList' => 'Die Liste wird mit allen Aufgaben gelöscht.\\nBist Du sicher?', + 'clearCompleted' => 'Alle abgeschlossenen Aufgaben dieser Liste werden gelöscht.\\nBist Du sicher?', + 'settingsSaved' => 'Einstellungen gespeichert. Aktualisierung...', + ); + + var $inc = array + ( + 'htab_newtask' => 'Neue Aufgabe', + 'htab_search' => 'Suche', + 'btn_add' => 'Hinzufügen', + 'btn_search' => 'Suche', + 'advanced_add' => 'Erweitert', + 'searching' => 'Suche nach', + 'tasks' => 'Aufgabe', + 'taskdate_inline_created' => 'hinzugefügt am %s', + 'taskdate_inline_completed' => 'Erledigt am %s', + 'taskdate_inline_duedate' => 'Fällig am %s', + 'taskdate_created' => 'Erstellt', + 'taskdate_completed' => 'Erledigt', + 'go_back' => '<< Zurück', + 'edit_task' => 'Aufgabe bearbeiten', + 'add_task' => 'Neue Aufgabe', + 'priority' => 'Priorität', + 'task' => 'Aufgabe', + 'note' => 'Notiz', + 'tags' => 'Schlagwörter', + 'save' => 'Speichern', + 'cancel' => 'Abbrechen', + 'password' => 'Passwort', + 'btn_login' => 'Login', + 'a_login' => 'Login', + 'a_logout' => 'Logout', + 'public_tasks' => 'Öffentliche Aufgabe', + 'tagcloud' => 'Tags', + 'tagfilter_cancel' => 'Filter aufheben', + 'sortByHand' => 'Manuell sortieren', + 'sortByPriority' => 'Nach Priorität sortieren', + 'sortByDueDate' => 'Nach Fälligkeitsdatum sortieren', + 'sortByDateCreated' => 'Nach Erstelldatum sortieren', + 'sortByDateModified' => 'Nach Änderungsdatum sortieren', + 'due' => 'Fällig', + 'daysago' => 'vor %d Tagen', + 'indays' => 'in %d Tagen', + 'months_short' => array('Jan','Feb','Mrz','Apr','Mai','Jun','Jul','Aug','Sep','Okt','Nov','Dez'), + 'months_long' => array('Januar','Februar','März','April','Mai','Juni','Juli','August','September','Oktober','November','Dezember'), + 'days_min' => array('So','Mo','Di','Mi','Do','Fr','Sa'), + 'days_long' => array('Sonntag','Montag','Dienstag','Mittwoch','Donnerstag','Freitag','Samstag'), + 'today' => 'heute', + 'yesterday' => 'gestern', + 'tomorrow' => 'morgen', + 'f_past' => 'Überfällig', + 'f_today' => 'Heute und morgen', + 'f_soon' => 'Bald', + 'action_edit' => 'Bearbeiten', + 'action_note' => 'Notiz bearbeiten', + 'action_delete' => 'Löschen', + 'action_priority' => 'Priorität', + 'action_move' => 'Verschieben nach', + 'notes' => 'Notizen:', + 'notes_show' => 'Anzeigen', + 'notes_hide' => 'Verbergen', + 'list_new' => 'Neue Liste', + 'list_rename' => 'Liste umbenennen', + 'list_delete' => 'Liste löschen', + 'list_publish' => 'Liste veröffentlichen', + 'list_showcompleted' => 'Abgeschlossene Aufgaben anzeigen', + 'list_clearcompleted' => 'Abgeschlossene Aufgaben löschen', + 'list_select' => 'Liste auswählen', + 'list_export' => 'Export', + 'list_export_csv' => 'CSV', + 'list_export_ical' => 'iCalendar', + 'list_rssfeed' => 'RSS Feed', + 'alltags' => 'Alle Schlagwörter:', + 'alltags_show' => 'Alle anzeigen', + 'alltags_hide' => 'Alle verbergen', + 'a_settings' => 'Einstellungen', + 'rss_feed' => 'RSS Feed', + 'feed_title' => '%s', + 'feed_completed_tasks' => 'Abgeschlossene Aufgabe', + 'feed_modified_tasks' => 'Geänderte Aufgaben', + 'feed_new_tasks' => 'Neue Aufgaben', + 'alltasks' => 'Alle Aufgaben', + 'set_header' => 'Einstellungen', + 'set_title' => 'Titel', + 'set_title_descr' => '(angeben, um Standardtitel zu ändern)', + 'set_language' => 'Sprache', + 'set_protection' => 'Passwortschutz', + 'set_enabled' => 'Aktiviert', + 'set_disabled' => 'Deaktiviert', + 'set_newpass' => 'Neues Passwort', + 'set_newpass_descr' => '(leer lassen, um aktuelles Passwort nicht zu ändern)', + 'set_smartsyntax' => 'Smartsyntax', + 'set_smartsyntax_descr' => '(/Priorität/ Aufgabe /Schlagwörter/)', + 'set_timezone' => 'Zeitzone', + 'set_autotag' => 'Automatische Schlagwörter', + 'set_autotag_descr' => '(fügt Schlagwort des aktuellen Filters automatisch der neu erstellten Aufgabe hinzu)', + 'set_sessions' => 'Sessionhandling-Mechanismus', + 'set_sessions_php' => 'PHP', + 'set_sessions_files' => 'Dateien', + 'set_firstdayofweek' => 'Erster Tag der Woche', + 'set_custom' => 'benutzerdefiniert', + 'set_date' => 'Datumsformat', + 'set_date2' => 'Kurzes Datumsformat', + 'set_shortdate' => 'Kurzes Datumsformat (aktuelles Jahr)', + 'set_clock' => 'Zeitformat', + 'set_12hour' => '12 Stunden', + 'set_24hour' => '24 Stunden', + 'set_submit' => 'Änderungen speichern', + 'set_cancel' => 'Abbrechen', + 'set_showdate' => 'Aufgabendatum in Liste anzeigen', + ); +} diff --git a/sources/www/lang/en.php b/sources/www/lang/en.php new file mode 100644 index 0000000..d840aae --- /dev/null +++ b/sources/www/lang/en.php @@ -0,0 +1,140 @@ + "Are you sure you want to delete the task?", + 'confirmLeave' => "There can be unsaved data. Do you really want to leave?", + 'actionNoteSave' => "save", + 'actionNoteCancel' => "cancel", + 'error' => "Some error occurred (click for details)", + 'denied' => "Access denied", + 'invalidpass' => "Wrong password", + 'tagfilter' => "Tag:", + 'addList' => "Create new list", + 'renameList' => "Rename list", + 'deleteList' => "This will delete current list with all tasks in it.\\nAre you sure?", + 'clearCompleted' => "This will delete all completed tasks in the list.\\nAre you sure?", + 'settingsSaved' => "Settings saved. Reloading...", + ); + + var $inc = array + ( + 'htab_newtask' => "New task", + 'htab_search' => "Search", + 'btn_add' => "Add", + 'btn_search' => "Search", + 'advanced_add' => "Advanced", + 'searching' => "Searching for", + 'tasks' => "Tasks", + 'taskdate_inline_created' => "created at %s", + 'taskdate_inline_completed' => "Completed at %s", + 'taskdate_inline_duedate' => "Due %s", + 'taskdate_created' => "Created", + 'taskdate_completed' => "Completed", + 'go_back' => "<< Back", + 'edit_task' => "Edit Task", + 'add_task' => "New Task", + 'priority' => "Priority", + 'task' => "Task", + 'note' => "Note", + 'tags' => "Tags", + 'save' => "Save", + 'cancel' => "Cancel", + 'password' => "Password", + 'btn_login' => "Login", + 'a_login' => "Login", + 'a_logout' => "Logout", + 'public_tasks' => "Public Tasks", + 'tagcloud' => "Tags", + 'tagfilter_cancel' => "cancel filter", + 'sortByHand' => "Sort by hand", + 'sortByPriority' => "Sort by priority", + 'sortByDueDate' => "Sort by due date", + 'sortByDateCreated' => "Sort by date created", + 'sortByDateModified' => "Sort by date modified", + 'due' => "Due", + 'daysago' => "%d days ago", + 'indays' => "in %d days", + 'months_short' => array("Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"), + 'months_long' => array("January","February","March","April","May","June","July","August","September","October","November","December"), + 'days_min' => array("Su","Mo","Tu","We","Th","Fr","Sa"), + 'days_long' => array("Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"), + 'today' => "today", + 'yesterday' => "yesterday", + 'tomorrow' => "tomorrow", + 'f_past' => "Overdue", + 'f_today' => "Today and tomorrow", + 'f_soon' => "Soon", + 'action_edit' => "Edit", + 'action_note' => "Edit Note", + 'action_delete' => "Delete", + 'action_priority' => "Priority", + 'action_move' => "Move to", + 'notes' => "Notes:", + 'notes_show' => "Show", + 'notes_hide' => "Hide", + 'list_new' => "New list", + 'list_rename' => "Rename list", + 'list_delete' => "Delete list", + 'list_publish' => "Publish list", + 'list_showcompleted' => "Show completed tasks", + 'list_clearcompleted' => "Clear completed tasks", + 'list_select' => "Select list", + 'list_export' => "Export", + 'list_export_csv' => "CSV", + 'list_export_ical' => "iCalendar", + 'list_rssfeed' => "RSS Feed", + 'alltags' => "All tags:", + 'alltags_show' => "Show all", + 'alltags_hide' => "Hide all", + 'a_settings' => "Settings", + 'rss_feed' => "RSS Feed", + 'feed_title' => "%s", + 'feed_completed_tasks' => "Completed tasks", + 'feed_modified_tasks' => "Modified tasks", + 'feed_new_tasks' => "New tasks", + 'alltasks' => "All tasks", + + /* Settings */ + 'set_header' => "Settings", + 'set_title' => "Title", + 'set_title_descr' => "(specify if you want to change default title)", + 'set_language' => "Language", + 'set_protection' => "Password protection", + 'set_enabled' => "Enabled", + 'set_disabled' => "Disabled", + 'set_newpass' => "New password", + 'set_newpass_descr' => "(leave blank if won't change current password)", + 'set_smartsyntax' => "Smart syntax", + 'set_smartsyntax_descr' => "(/priority/ task /tags/)", + 'set_timezone' => "Time zone", + 'set_autotag' => "Autotagging", + 'set_autotag_descr' => "(automatically adds tag of current tag filter to newly created task)", + 'set_sessions' => "Session handling mechanism", + 'set_sessions_php' => "PHP", + 'set_sessions_files' => "Files", + 'set_firstdayofweek' => "First day of week", + 'set_custom' => "Custom", + 'set_date' => "Date format", + 'set_date2' => "Short Date format", + 'set_shortdate' => "Short Date (current year)", + 'set_clock' => "Clock format", + 'set_12hour' => "12-hour", + 'set_24hour' => "24-hour", + 'set_submit' => "Submit changes", + 'set_cancel' => "Cancel", + 'set_showdate' => "Show task date in list", + ); +} diff --git a/sources/www/lang/fr.php b/sources/www/lang/fr.php new file mode 100644 index 0000000..5854317 --- /dev/null +++ b/sources/www/lang/fr.php @@ -0,0 +1,137 @@ + 'Êtes-vous sûr de vouloir supprimer la tâche ?', + 'confirmLeave' => 'Il peut y avoir des données non enregistrées. Voulez-vous vraiment quitter ?', + 'actionNoteSave' => 'sauvegarder', + 'actionNoteCancel' => 'annuler', + 'error' => 'Il y a eu des erreurs (cliquez pour plus de détails)', + 'denied' => 'Accès refusé', + 'invalidpass' => 'Mauvais mot de passe', + 'tagfilter' => 'Mots-clefs:', + 'addList' => 'Créer une nouvelle liste', + 'renameList' => 'Renommer la liste', + 'deleteList' => 'Cela supprimera la liste actuelle avec toutes les tâches qu’elle contient.\\nÊtes-vous sûr ?', + 'clearCompleted' => 'Cela supprimera toutes les tâches achevées de la liste.\\nÊtes-vous sûr ?', + 'settingsSaved' => 'Réglages sauvegardés. Chargement...', + ); + + var $inc = array + ( + 'htab_newtask' => 'Nouvelle tâche', + 'htab_search' => 'Recherche', + 'btn_add' => 'Ajouter', + 'btn_search' => 'Rechercher', + 'advanced_add' => 'Avancé', + 'searching' => 'Recherche de', + 'tasks' => 'Tâches', + 'taskdate_inline_created' => 'créée le %s', + 'taskdate_inline_completed' => 'Achevée le %s', + 'taskdate_inline_duedate' => 'Échéance %s', + 'taskdate_created' => 'Créée', + 'taskdate_completed' => 'Achevée', + 'go_back' => '<< Retour', + 'edit_task' => 'Éditer la tâche', + 'add_task' => 'Nouvelle tâche', + 'priority' => 'Priorité', + 'task' => 'Tâche', + 'note' => 'Note', + 'save' => 'Sauvegarder', + 'cancel' => 'Annuler', + 'password' => 'Mot de passe', + 'btn_login' => 'Connexion', + 'a_login' => 'Connexion', + 'a_logout' => 'Déconnexion', + 'public_tasks' => 'Tâches publiques', + 'tags' => 'Mots-clefs', + 'tagfilter_cancel' => 'Annuler le filtre', + 'sortByHand' => 'Trier manuellement', + 'sortByPriority' => 'Trier par priorité', + 'sortByDueDate' => 'Trier par date d’échéance', + 'sortByDateCreated' => 'Trier par date de création', + 'sortByDateModified' => 'Trier par date de modification', + 'due' => 'Échéance', + 'daysago' => 'il y a %d jours', + 'indays' => 'dans %d jours', + 'months_short' => array('Jan','Fév','Mar','Avr','Mai','Juin','Juil','Août','Sep','Oct','Nov','Déc'), + 'months_long' => array('Janvier','Février','Mars','Avril','Mai','Juin','Juillet','Août','Septembre','Octobre','Novembre','Décembre'), + 'days_min' => array('Dim','Lun','Mar','Mer','Jeu','Ven','Sam'), + 'days_long' => array('Dimanche','Lundi','Mardi','Mercredi','Jeudi','Vendredi','Samedi'), + 'today' => 'aujourd’hui', + 'yesterday' => 'hier', + 'tomorrow' => 'demain', + 'f_past' => 'En retard', + 'f_today' => 'Aujourd’hui et demain', + 'f_soon' => 'Bientôt', + 'action_edit' => 'Éditer', + 'action_note' => 'Éditer la note', + 'action_delete' => 'Supprimer', + 'action_priority' => 'Priorité', + 'action_move' => 'Envoyer vers', + 'notes' => 'Notes:', + 'notes_show' => 'Montrer', + 'notes_hide' => 'Cacher', + 'list_new' => 'Nouvelle liste', + 'list_rename' => 'Renommer la liste', + 'list_delete' => 'Supprimer la liste', + 'list_publish' => 'Publier la liste', + 'list_showcompleted' => 'Montrer les tâches achevées', + 'list_clearcompleted' => 'Effacer les tâches achevées', + 'list_select' => 'Sélectionner la liste', + 'list_export' => 'Exporter', + 'list_export_csv' => 'CSV', + 'list_export_ical' => 'iCalendar', + 'list_rssfeed' => 'Flux RSS', + 'alltags' => 'Tous les mots-clefs:', + 'alltags_show' => 'Tout montrer', + 'alltags_hide' => 'Tout cacher', + 'a_settings' => 'Configuration', + 'rss_feed' => 'Flux RSS', + 'feed_title' => '%s', + 'feed_completed_tasks' => 'Tâches achevées', + 'feed_modified_tasks' => 'Tâches modifiées', + 'feed_new_tasks' => 'Nouvelles tâches', + 'alltasks' => 'Toutes les tâches', + 'set_header' => 'Configuration', + 'set_title' => 'Titre', + 'set_title_descr' => '(Spécifiez si vous souhaitez changer le titre par défaut)', + 'set_language' => 'Langue', + 'set_protection' => 'Protection par mot de passe', + 'set_enabled' => 'Activé', + 'set_disabled' => 'Désactivé', + 'set_newpass' => 'Nouveau mot de passe', + 'set_newpass_descr' => '(laissez blanc pour ne pas modifier le mot de passe actuel)', + 'set_smartsyntax' => 'Syntaxe rapide', + 'set_smartsyntax_descr' => '(/priorité/ tâche /mots-clefs/)', + 'set_timezone' => 'Fuseaux horaires', + 'set_autotag' => 'Mots-clefs automatiques', + 'set_autotag_descr' => '(ajoute automatiquement les mots-clefs aux nouvelles tâches parmis ceux que vous avez déjà définis)', + 'set_sessions' => 'Mécanisme de session', + 'set_sessions_php' => 'PHP', + 'set_sessions_files' => 'Fichiers', + 'set_firstdayofweek' => 'Premier jour de la semaine', + 'set_custom' => 'Personnalisé', + 'set_date' => 'Format de date', + 'set_date2' => 'Format de date court', + 'set_shortdate' => 'Date courte (année actuelle)', + 'set_clock' => 'Format de l’heure', + 'set_12hour' => '12 heures', + 'set_24hour' => '24 heures', + 'set_submit' => 'Sauvegarder la configuration', + 'set_cancel' => 'Annuler', + 'set_showdate' => 'Afficher la date dans la liste', + ); +} diff --git a/sources/www/lang/ru.php b/sources/www/lang/ru.php new file mode 100644 index 0000000..92fe399 --- /dev/null +++ b/sources/www/lang/ru.php @@ -0,0 +1,138 @@ + 'Вы действительно хотите удалить задачу?', + 'confirmLeave' => 'На странице могут быть несохраненные данные. Вы действительно хотите закрыть страницу?', + 'actionNoteSave' => 'сохранить', + 'actionNoteCancel' => 'отмена', + 'error' => 'Ошибка', + 'denied' => 'Доступ запрещен', + 'invalidpass' => 'Неверный пароль', + 'tagfilter' => 'Тег:', + 'addList' => 'Новый список', + 'renameList' => 'Переименовать список', + 'deleteList' => 'Вы действительно хотите удалить этот список со всеми задачами?', + 'clearCompleted' => 'Удалить все выполненные задачи из списка?', + 'settingsSaved' => 'Настройки сохранены. Перезагрузка...', + ); + + var $inc = array + ( + 'htab_newtask' => 'Новая задача', + 'htab_search' => 'Поиск', + 'btn_add' => 'Добавить', + 'btn_search' => 'Искать', + 'advanced_add' => 'Расширенная форма', + 'searching' => 'Поиск', + 'tasks' => 'Задачи', + 'taskdate_inline_created' => 'добавлена %s', + 'taskdate_inline_completed' => 'Завершена %s', + 'taskdate_inline_duedate' => 'В срок %s', + 'taskdate_created' => 'Дата создания', + 'taskdate_completed' => 'Дата завершения', + 'go_back' => '<< Назад', + 'edit_task' => 'Редактирование задачи', + 'add_task' => 'Новая задача', + 'priority' => 'Приоритет', + 'task' => 'Задача', + 'note' => 'Заметка', + 'tags' => 'Теги', + 'save' => 'Сохранить', + 'cancel' => 'Отмена', + 'password' => 'Пароль', + 'btn_login' => 'Войти', + 'a_login' => 'Вход', + 'a_logout' => 'Выйти', + 'public_tasks' => 'Опубликованные задачи', + 'tagcloud' => 'Теги', + 'tagfilter_cancel' => 'отменить фильтр по тегу', + 'sortByHand' => 'Сортировка вручную', + 'sortByPriority' => 'Сортировка по приоритету', + 'sortByDueDate' => 'Сортировка по сроку', + 'sortByDateCreated' => 'Сортировка по дате добавления', + 'sortByDateModified' => 'Сортировка по дате изменения', + 'due' => 'Срок', + 'daysago' => '%d дн. назад', + 'indays' => 'через %d дн.', + 'months_short' => array('Янв','Фев','Мар','Апр','Май','Июн','Июл','Авг','Сен','Окт','Ноя','Дек'), + 'months_long' => array('Январь','Февраль','Март','Апрель','Май','Июнь','Июль','Август','Сентябрь','Октябрь','Ноябрь','Декабрь'), + 'days_min' => array('Вс','Пн','Вт','Ср','Чт','Пт','Сб'), + 'days_long' => array('Воскресенье','Понедельник','Вторник','Среда','Четверг','Пятница','Суббота'), + 'today' => 'сегодня', + 'yesterday' => 'вчера', + 'tomorrow' => 'завтра', + 'f_past' => 'Просроченные', + 'f_today' => 'Сегодня и завтра', + 'f_soon' => 'Скоро', + 'action_edit' => 'Редактировать', + 'action_note' => 'Заметка', + 'action_delete' => 'Удалить', + 'action_priority' => 'Приоритет', + 'action_move' => 'Переместить в', + 'notes' => 'Заметки:', + 'notes_show' => 'Показать', + 'notes_hide' => 'Скрыть', + 'list_new' => 'Новый список', + 'list_rename' => 'Переименовать список', + 'list_delete' => 'Удалить список', + 'list_publish' => 'Опубликовать список', + 'list_showcompleted' => 'Показать завершенные задачи', + 'list_clearcompleted' => 'Удалить завершенные задачи', + 'list_select' => 'Выбрать список', + 'list_export' => 'Экспортировать', + 'list_export_csv' => 'CSV', + 'list_export_ical' => 'iCalendar', + 'list_rssfeed' => 'RSS-лента', + 'alltags' => 'Все теги:', + 'alltags_show' => 'Показать все', + 'alltags_hide' => 'Скрыть все', + 'a_settings' => 'Настройки', + 'rss_feed' => 'RSS-лента', + 'feed_title' => '%s', + 'feed_completed_tasks' => 'Завершенные задачи', + 'feed_modified_tasks' => 'Изменившиеся задачи', + 'feed_new_tasks' => 'Новые задачи', + 'alltasks' => 'Все задачи', + 'set_header' => 'Настройки', + 'set_title' => 'Заголовок страницы', + 'set_title_descr' => '(если поле не заполнено, будет использован заголовок по-умолчанию)', + 'set_language' => 'Язык (Language)', + 'set_protection' => 'Парольная защита', + 'set_enabled' => 'Включено', + 'set_disabled' => 'Выключено', + 'set_newpass' => 'Новый пароль', + 'set_newpass_descr' => '(не заполняйте поле если не хотите менять текущий пароль)', + 'set_smartsyntax' => 'Smart syntax', + 'set_smartsyntax_descr' => '(возможность использовать синтаксис: /приоритет/ задача /теги/)', + 'set_timezone' => 'Часовой пояс', + 'set_autotag' => 'Autotagging', + 'set_autotag_descr' => '(автодобавление текущего тега из фильтра в новую задачу)', + 'set_sessions' => 'Хранилище сессий', + 'set_sessions_php' => 'PHP', + 'set_sessions_files' => 'Файлы', + 'set_firstdayofweek' => 'Первый день недели', + 'set_custom' => 'другой', + 'set_date' => 'Формат даты', + 'set_date2' => 'Формат короткой даты', + 'set_shortdate' => 'Короткая дата (в текущем году)', + 'set_clock' => 'Формат часов', + 'set_12hour' => '12-часовой', + 'set_24hour' => '24-часовой', + 'set_submit' => 'Сохранить изменения', + 'set_cancel' => 'Отмена', + 'set_showdate' => 'Показывать дату создания задачи', + ); +} diff --git a/sources/www/mytinytodo.js b/sources/www/mytinytodo.js new file mode 100644 index 0000000..a6bd093 --- /dev/null +++ b/sources/www/mytinytodo.js @@ -0,0 +1,2159 @@ +/* + This file is part of myTinyTodo. + (C) Copyright 2009-2010 Max Pozdeev + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +(function(){ + +var taskList = new Array(), taskOrder = new Array(); +var filter = { compl:0, search:'', due:'' }; +var sortOrder; //save task order before dragging +var searchTimer; +var objPrio = {}; +var selTask = 0; +var flag = { needAuth:false, isLogged:false, tagsChanged:true, readOnly:false, editFormChanged:false }; +var taskCnt = { total:0, past: 0, today:0, soon:0 }; +var tabLists = { + _lists: {}, + _length: 0, + _order: [], + _alltasks: {}, + clear: function(){ + this._lists = {}; this._length = 0; this._order = []; + this._alltasks = { id:-1, showCompl:0, sort:3 }; + }, + length: function(){ return this._length; }, + exists: function(id){ if(this._lists[id] || id==-1) return true; else return false; }, + add: function(list){ this._lists[list.id] = list; this._length++; this._order.push(list.id); }, + replace: function(list){ this._lists[list.id] = list; }, + get: function(id){ if(id==-1) return this._alltasks; else return this._lists[id]; }, + getAll: function(){ var r = []; for(var i in this._order) { r.push(this._lists[this._order[i]]); }; return r; }, + reorder: function(order){ this._order = order; } +}; +var curList = 0; +var tagsList = []; + +var mytinytodo = window.mytinytodo = _mtt = { + + theme: { + newTaskFlashColor: '#ffffaa', + editTaskFlashColor: '#bbffaa', + msgFlashColor: '#ffffff' + }, + + actions: {}, + menus: {}, + mttUrl: '', + templateUrl: '', + options: { + openList: 0, + singletab: false, + autotag: false, + tagPreview: true, + tagPreviewDelay: 700, //milliseconds + saveShowNotes: false, + firstdayofweek: 1, + touchDevice: false + }, + + timers: { + previewtag: 0 + }, + + lang: { + __lang: null, + + daysMin: [], + daysLong: [], + monthsShort: [], + monthsLong: [], + + get: function(v) { + if(this.__lang[v]) return this.__lang[v]; + else return v; + }, + + init: function(lang) + { + this.__lang = lang; + this.daysMin = this.__lang.daysMin; + this.daysLong = this.__lang.daysLong; + this.monthsShort = this.__lang.monthsMin; + this.monthsLong = this.__lang.monthsLong; + } + }, + + pages: { + current: { page:'tasks', pageClass:'' }, + prev: [] + }, + + // procs + init: function(options) + { + jQuery.extend(this.options, options); + + flag.needAuth = options.needAuth ? true : false; + flag.isLogged = options.isLogged ? true : false; + + if(this.options.showdate) $('#page_tasks').addClass('show-inline-date'); + if(this.options.singletab) $('#lists .mtt-tabs').addClass('mtt-tabs-only-one'); + + this.parseAnchor(); + + // handlers + $('.mtt-tabs-add-button').click(function(){ + addList(); + }); + + $('.mtt-tabs-select-button').click(function(event){ + if(event.metaKey || event.ctrlKey) { + // toggle singetab interface + _mtt.applySingletab(!_mtt.options.singletab); + return false; + } + if(!_mtt.menus.selectlist) _mtt.menus.selectlist = new mttMenu('slmenucontainer', {onclick:slmenuSelect}); + _mtt.menus.selectlist.show(this); + }); + + + $('#newtask_form').submit(function(){ + submitNewTask(this); + return false; + }); + + $('#newtask_submit').click(function(){ + $('#newtask_form').submit(); + }); + + $('#newtask_adv').click(function(){ + showEditForm(1); + return false; + }); + + $('#task').keydown(function(event){ + if(event.keyCode == 27) { + $(this).val(''); + } + }).focusin(function(){ + $('#task_placeholder').removeClass('placeholding'); + $('#toolbar').addClass('mtt-intask'); + }).focusout(function(){ + if('' == $(this).val()) $('#task_placeholder').addClass('placeholding'); + $('#toolbar').removeClass('mtt-intask'); + }); + + + $('#search_form').submit(function(){ + searchTasks(1); + return false; + }); + + $('#search_close').click(function(){ + liveSearchToggle(0); + return false; + }); + + $('#search').keyup(function(event){ + if(event.keyCode == 27) return; + if($(this).val() == '') $('#search_close').hide(); //actual value is only on keyup + else $('#search_close').show(); + clearTimeout(searchTimer); + searchTimer = setTimeout(function(){searchTasks()}, 400); + }) + .keydown(function(event){ + if(event.keyCode == 27) { // cancel on Esc (NB: no esc event on keypress in Chrome and on keyup in Opera) + if($(this).val() != '') { + $(this).val(''); + $('#search_close').hide(); + searchTasks(); + } + else { + liveSearchToggle(0); + } + return false; //need to return false in firefox (for AJAX?) + } + }).focusin(function(){ + $('#toolbar').addClass('mtt-insearch'); + $(this).focus(); + }).focusout(function(){ + $('#toolbar').removeClass('mtt-insearch'); + }); + + + $('#taskview').click(function(){ + if(!_mtt.menus.taskview) _mtt.menus.taskview = new mttMenu('taskviewcontainer'); + _mtt.menus.taskview.show(this); + }); + + $('#mtt_filters .tag-filter .mtt-filter-close').live('click', function(){ + cancelTagFilter($(this).attr('tagid')); + }); + + $('#tagcloudbtn').click(function(){ + if(!_mtt.menus.tagcloud) _mtt.menus.tagcloud = new mttMenu('tagcloud', { + beforeShow: function(){ + if(flag.tagsChanged) { + $('#tagcloudcontent').html(''); + $('#tagcloudload').show(); + loadTags(curList.id, function(){$('#tagcloudload').hide();}); + } + }, adjustWidth:true + }); + _mtt.menus.tagcloud.show(this); + }); + + $('#tagcloudcancel').click(function(){ + if(_mtt.menus.tagcloud) _mtt.menus.tagcloud.close(); + }); + + $('#tagcloudcontent .tag').live('click', function(){ + addFilterTag($(this).attr('tag'), $(this).attr('tagid')); + if(_mtt.menus.tagcloud) _mtt.menus.tagcloud.close(); + return false; + }); + + $('#mtt-notes-show').click(function(){ + toggleAllNotes(1); + this.blur(); + return false; + }); + + $('#mtt-notes-hide').click(function(){ + toggleAllNotes(0); + this.blur(); + return false; + }); + + $('#taskviewcontainer li').click(function(){ + if(this.id == 'view_tasks') setTaskview(0); + else if(this.id == 'view_past') setTaskview('past'); + else if(this.id == 'view_today') setTaskview('today'); + else if(this.id == 'view_soon') setTaskview('soon'); + }); + + + // Tabs + $('#lists li.mtt-tab').live('click', function(event){ + if(event.metaKey || event.ctrlKey) { + // hide the tab + hideTab(this); + return false; + } + tabSelect(this); + return false; + }); + + $('#list_all').click(function(event){ + if(event.metaKey || event.ctrlKey) { + // hide the tab + hideTab(-1); + return false; + } + tabSelect(-1); + return false; + }); + + $('#lists li.mtt-tab .list-action').live('click', function(){ + listMenu(this); + return false; //stop bubble to tab click + }); + + $('#list_all .list-action').click(function(event){ + listMenu(this); + return false; //stop bubble to tab click + }); + + //Priority popup + $('#priopopup .prio-neg-1').click(function(){ + prioClick(-1,this); + }); + + $('#priopopup .prio-zero').click(function(){ + prioClick(0,this); + }); + + $('#priopopup .prio-pos-1').click(function(){ + prioClick(1,this); + }); + + $('#priopopup .prio-pos-2').click(function(){ + prioClick(2,this); + }); + + $('#priopopup').mouseleave(function(){ + $(this).hide()} + ); + + + // edit form handlers + $('#alltags_show').click(function(){ + toggleEditAllTags(1); + return false; + }); + + $('#alltags_hide').click(function(){ + toggleEditAllTags(0); + return false; + }); + + $('#taskedit_form').submit(function(){ + return saveTask(this); + }); + + $('#alltags .tag').live('click', function(){ + addEditTag($(this).attr('tag')); + return false; + }); + + $("#duedate").datepicker({ + dateFormat: _mtt.duedatepickerformat(), + firstDay: _mtt.options.firstdayofweek, + showOn: 'button', + buttonImage: _mtt.templateUrl + 'images/calendar.png', buttonImageOnly: true, + constrainInput: false, + duration:'', + dayNamesMin:_mtt.lang.daysMin, dayNames:_mtt.lang.daysLong, monthNamesShort:_mtt.lang.monthsLong + }); + + $("#edittags").autocomplete('ajax.php?suggestTags', {scroll: false, multiple: true, selectFirst:false, max:8, extraParams:{list:function(){ var taskId = document.getElementById('taskedit_form').id.value; return taskList[taskId].listId; }}}); + + $('#taskedit_form').find('select,input,textarea').bind('change keypress', function(){ + flag.editFormChanged = true; + }); + + // tasklist handlers + $("#tasklist").bind("click", tasklistClick); + + $('#tasklist li').live('dblclick', function(){ + //clear selection + if(document.selection && document.selection.empty && document.selection.createRange().text) document.selection.empty(); + else if(window.getSelection) window.getSelection().removeAllRanges(); + + var li = findParentNode(this, 'LI'); + if(li && li.id) { + var id = li.id.split('_',2)[1]; + if(id) editTask(parseInt(id)); + } + }); + + $('#tasklist .taskactionbtn').live('click', function(){ + var id = parseInt(getLiTaskId(this)); + if(id) taskContextMenu(this, id); + return false; + }); + + $('#tasklist input[type=checkbox]').live('click', function(){ + var id = parseInt(getLiTaskId(this)); + if(id) completeTask(id, this); + //return false; + }); + + $('#tasklist .task-toggle').live('click', function(){ + var id = getLiTaskId(this); + if(id) $('#taskrow_'+id).toggleClass('task-expanded'); + return false; + }); + + $('#tasklist .tag').live('click', function(event){ + clearTimeout(_mtt.timers.previewtag); + $('#tasklist li').removeClass('not-in-tagpreview'); + addFilterTag($(this).attr('tag'), $(this).attr('tagid'), (event.metaKey || event.ctrlKey ? true : false) ); + return false; + }); + + if(!this.options.touchDevice) { + $('#tasklist .task-prio').live('mouseover mouseout', function(event){ + var id = parseInt(getLiTaskId(this)); + if(!id) return; + if(event.type == 'mouseover') prioPopup(1, this, id); + else prioPopup(0, this); + }); + } + + $('#tasklist .mtt-action-note-cancel').live('click', function(){ + var id = parseInt(getLiTaskId(this)); + if(id) cancelTaskNote(id); + return false; + }); + + $('#tasklist .mtt-action-note-save').live('click', function(){ + var id = parseInt(getLiTaskId(this)); + if(id) saveTaskNote(id); + return false; + }); + + if(this.options.tagPreview) { + $('#tasklist .tag').live('mouseover mouseout', function(event){ + var cl = 'tag-id-' + $(this).attr('tagid'); + var sel = (event.metaKey || event.ctrlKey) ? 'li.'+cl : 'li:not(.'+cl+')'; + if(event.type == 'mouseover') { + _mtt.timers.previewtag = setTimeout( function(){$('#tasklist '+sel).addClass('not-in-tagpreview');}, _mtt.options.tagPreviewDelay); + } + else { + clearTimeout(_mtt.timers.previewtag); + $('#tasklist li').removeClass('not-in-tagpreview'); + } + }); + } + + $("#tasklist").sortable({ + items:'> :not(.task-completed)', cancel:'span,input,a,textarea', + delay:150, start:sortStart, update:orderChanged, + placeholder:'mtt-task-placeholder' + }); + + $("#lists ul").sortable({delay:150, update:listOrderChanged}); + this.applySingletab(); + + + // AJAX Errors + $('#msg').ajaxSend(function(r,s){ + $("#msg").hide().removeClass('mtt-error mtt-info').find('.msg-details').hide(); + $("#loading").show(); + }); + + $('#msg').ajaxStop(function(r,s){ + $("#loading").fadeOut(); + }); + + $('#msg').ajaxError(function(event, request, settings){ + var errtxt; + if(request.status == 0) errtxt = 'Bad connection'; + else if(request.status != 200) errtxt = 'HTTP: '+request.status+'/'+request.statusText; + else errtxt = request.responseText; + flashError(_mtt.lang.get('error'), errtxt); + }); + + + // Error Message details + $("#msg>.msg-text").click(function(){ + $("#msg>.msg-details").toggle(); + }); + + + // Authorization + $('#bar_login').click(function(){ + showAuth(this); + return false; + }); + + $('#bar_logout').click(function(){ + logout(); + return false; + }); + + $('#login_form').submit(function(){ + doAuth(this); + return false; + }); + + + // Settings + $("#settings").click(showSettings); + $("#settings_form").live('submit', function() { + saveSettings(this); + return false; + }); + + $(".mtt-back-button").live('click', function(){ _mtt.pageBack(); this.blur(); return false; } ); + + $(window).bind('beforeunload', function() { + if(_mtt.pages.current.page == 'taskedit' && flag.editFormChanged) { + return _mtt.lang.get('confirmLeave'); + } + }); + + + // tab menu + this.addAction('listSelected', tabmenuOnListSelected); + + // task context menu + this.addAction('listsLoaded', cmenuOnListsLoaded); + this.addAction('listRenamed', cmenuOnListRenamed); + this.addAction('listAdded', cmenuOnListAdded); + this.addAction('listSelected', cmenuOnListSelected); + this.addAction('listOrderChanged', cmenuOnListOrderChanged); + this.addAction('listHidden', cmenuOnListHidden); + + // select list menu + this.addAction('listsLoaded', slmenuOnListsLoaded); + this.addAction('listRenamed', slmenuOnListRenamed); + this.addAction('listAdded', slmenuOnListAdded); + this.addAction('listSelected', slmenuOnListSelected); + this.addAction('listHidden', slmenuOnListHidden); + + return this; + }, + + log: function(v) + { + console.log.apply(this, arguments); + }, + + addAction: function(action, proc) + { + if(!this.actions[action]) this.actions[action] = new Array(); + this.actions[action].push(proc); + }, + + doAction: function(action, opts) + { + if(!this.actions[action]) return; + for(var i in this.actions[action]) { + this.actions[action][i](opts); + } + }, + + setOptions: function(opts) { + jQuery.extend(this.options, opts); + }, + + loadLists: function(onInit) + { + if(filter.search != '') { + filter.search = ''; + $('#searchbarkeyword').text(''); + $('#searchbar').hide(); + } + $('#page_tasks').hide(); + $('#tasklist').html(''); + + tabLists.clear(); + + this.db.loadLists(null, function(res) + { + var ti = ''; + var openListId = 0; + if(res && res.total) + { + // open required or first non-hidden list + for(var i=0; i
    • '; + }); + } + + if(openListId) { + $('#mtt_body').removeClass('no-lists'); + $('.mtt-need-list').removeClass('mtt-item-disabled'); + } + else { + curList = 0; + $('#mtt_body').addClass('no-lists'); + $('.mtt-need-list').addClass('mtt-item-disabled'); + } + + _mtt.options.openList = 0; + $('#lists ul').html(ti); + $('#lists').show(); + _mtt.doAction('listsLoaded'); + tabSelect(openListId); + + $('#page_tasks').show(); + + }); + + if(onInit) updateAccessStatus(); + }, + + duedatepickerformat: function() + { + if(!this.options.duedatepickerformat) return 'yy-mm-dd'; + + var s = this.options.duedatepickerformat.replace(/(.)/g, function(t,s) { + switch(t) { + case 'Y': return 'yy'; + case 'y': return 'y'; + case 'd': return 'dd'; + case 'j': return 'd'; + case 'm': return 'mm'; + case 'n': return 'm'; + case '/': + case '.': + case '-': return t; + default: return ''; + } + }); + + if(s == '') return 'yy-mm-dd'; + return s; + }, + + errorDenied: function() + { + flashError(this.lang.get('denied')); + }, + + pageSet: function(page, pageClass) + { + var prev = this.pages.current; + prev.lastScrollTop = $(window).scrollTop(); + this.pages.prev.push(this.pages.current); + this.pages.current = {page:page, pageClass:pageClass}; + showhide($('#page_'+ this.pages.current.page).addClass('mtt-page-'+ this.pages.current.pageClass), $('#page_'+ prev.page)); + }, + + pageBack: function() + { + if(this.pages.current.page == 'tasks') return false; + var prev = this.pages.current; + this.pages.current = this.pages.prev.pop(); + showhide($('#page_'+ this.pages.current.page), $('#page_'+ prev.page).removeClass('mtt-page-'+prev.page.pageClass)); + $(window).scrollTop(this.pages.current.lastScrollTop); + }, + + applySingletab: function(yesno) + { + if(yesno == null) yesno = this.options.singletab; + else this.options.singletab = yesno; + + if(yesno) { + $('#lists .mtt-tabs').addClass('mtt-tabs-only-one'); + $("#lists ul").sortable('disable'); + } + else { + $('#lists .mtt-tabs').removeClass('mtt-tabs-only-one'); + $("#lists ul").sortable('enable'); + } + }, + + filter: { + _filters: [], + clear: function() { + this._filters = []; + $('#mtt_filters').html(''); + }, + addTag: function(tagId, tag, exclude) + { + for(var i in this._filters) { + if(this._filters[i].tagId && this._filters[i].tagId == tagId) return false; + } + this._filters.push({tagId:tagId, tag:tag, exclude:exclude}); + $('#mtt_filters').append(''+ + _mtt.lang.get('tagfilter')+''+tag+''); + return true; + }, + cancelTag: function(tagId) + { + for(var i in this._filters) { + if(this._filters[i].tagId && this._filters[i].tagId == tagId) { + this._filters.splice(i,1); + $('#mtt_filters .tag-filter.tag-id-'+tagId).remove(); + return true; + } + } + return false; + }, + getTags: function(withExcluded) + { + var a = []; + for(var i in this._filters) { + if(this._filters[i].tagId) { + if(this._filters[i].exclude && withExcluded) a.push('^'+ this._filters[i].tag); + else if(!this._filters[i].exclude) a.push(this._filters[i].tag) + } + } + return a.join(', '); + } + }, + + parseAnchor: function() + { + if(location.hash == '') return false; + var h = location.hash.substr(1); + var a = h.split("/"); + var p = {}; + var s = ''; + + for(var i=0; i 0) { + $('#lists ul').append('
    • '+ + ''+item.name+''+ + '
    • '); + mytinytodo.doAction('listAdded', item); + } + else _mtt.loadLists(); + }); +}; + +function renameCurList() +{ + if(!curList) return; + var r = prompt(_mtt.lang.get('renameList'), dehtml(curList.name)); + if(r == null || r == '') return; + + _mtt.db.request('renameList', {list:curList.id, name:r}, function(json){ + if(!parseInt(json.total)) return; + var item = json.list[0]; + curList = item; + tabLists.replace(item); + $('#lists ul>.mtt-tabs-selected>a').attr('title', item.name).find('span').html(item.name); + mytinytodo.doAction('listRenamed', item); + }); +}; + +function deleteCurList() +{ + if(!curList) return false; + var r = confirm(_mtt.lang.get('deleteList')); + if(!r) return; + + _mtt.db.request('deleteList', {list:curList.id}, function(json){ + if(!parseInt(json.total)) return; + _mtt.loadLists(); + }) +}; + +function publishCurList() +{ + if(!curList) return false; + _mtt.db.request('publishList', { list:curList.id, publish:curList.published?0:1 }, function(json){ + if(!parseInt(json.total)) return; + curList.published = curList.published?0:1; + if(curList.published) { + $('#btnPublish').addClass('mtt-item-checked'); + $('#btnRssFeed').removeClass('mtt-item-disabled'); + } + else { + $('#btnPublish').removeClass('mtt-item-checked'); + $('#btnRssFeed').addClass('mtt-item-disabled'); + } + }); +}; + + +function loadTasks(opts) +{ + if(!curList) return false; + setSort(curList.sort, 1); + opts = opts || {}; + if(opts.clearTasklist) { + $('#tasklist').html(''); + $('#total').html('0'); + } + + _mtt.db.request('loadTasks', { + list: curList.id, + compl: curList.showCompl, + sort: curList.sort, + search: filter.search, + tag: _mtt.filter.getTags(true), + setCompl: opts.setCompl + }, function(json){ + taskList.length = 0; + taskOrder.length = 0; + taskCnt.total = taskCnt.past = taskCnt.today = taskCnt.soon = 0; + var tasks = ''; + $.each(json.list, function(i,item){ + tasks += prepareTaskStr(item); + taskList[item.id] = item; + taskOrder.push(parseInt(item.id)); + changeTaskCnt(item, 1); + }); + if(opts.beforeShow && opts.beforeShow.call) { + opts.beforeShow(); + } + refreshTaskCnt(); + $('#tasklist').html(tasks); + }); +}; + + +function prepareTaskStr(item, noteExp) +{ + // — = — = — + var id = item.id; + var prio = item.prio; + return '
    • ' + + '
      '+"\n"+ + '
      '+ + '
      '+"\n"+ + '
      '+prepareDuedate(item)+ + ''+item.dateInline+'—'+ + ''+item.dateCompletedInline+'
      '+"\n"+ + '
      '+preparePrio(prio,id)+''+prepareHtml(item.title)+' '+ + (curList.id == -1 ? ''+ tabLists.get(item.listId).name +'' : '') + "\n" + + prepareTagsStr(item)+''+item.dateInlineTitle+'
      '+ + '
      '+ + '
      '+prepareHtml(item.note)+'
      '+ + ''+ + '
      '+ + "
    • \n"; +}; + + +function prepareHtml(s) +{ + // make URLs clickable + s = s.replace(/(^|\s|>)(www\.([\w\#$%&~\/.\-\+;:=,\?\[\]@]+?))(,|\.|:|)?(?=\s|"|<|>|\"|<|>|$)/gi, '$1$2$4'); + return s.replace(/(^|\s|>)((?:http|https|ftp):\/\/([\w\#$%&~\/.\-\+;:=,\?\[\]@]+?))(,|\.|:|)?(?=\s|"|<|>|\"|<|>|$)/ig, '$1$2$4'); +}; + +function preparePrio(prio,id) +{ + var cl =''; var v = ''; + if(prio < 0) { cl = 'prio-neg prio-neg-'+Math.abs(prio); v = '−'+Math.abs(prio); } // − = − = − + else if(prio > 0) { cl = 'prio-pos prio-pos-'+prio; v = '+'+prio; } + else { cl = 'prio-zero'; v = '±0'; } // ± = ± = ± + return ''+v+''; +}; + +function prepareTagsStr(item) +{ + if(!item.tags || item.tags == '') return ''; + var a = item.tags.split(','); + if(!a.length) return ''; + var b = item.tags_ids.split(',') + for(var i in a) { + a[i] = ''+a[i]+''; + } + return ''+a.join(', ')+''; +}; + +function prepareTagsClass(ids) +{ + if(!ids || ids == '') return ''; + var a = ids.split(','); + if(!a.length) return ''; + for(var i in a) { + a[i] = 'tag-id-'+a[i]; + } + return ' '+a.join(' '); +}; + +function prepareDuedate(item) +{ + if(!item.duedate) return ''; + return ' '+item.dueStr+''; +}; + + +function submitNewTask(form) +{ + if(form.task.value == '') return false; + _mtt.db.request('newTask', { list:curList.id, title: form.task.value, tag:_mtt.filter.getTags() }, function(json){ + if(!json.total) return; + $('#total').text( parseInt($('#total').text()) + 1 ); + taskCnt.total++; + form.task.value = ''; + var item = json.list[0]; + taskList[item.id] = item; + taskOrder.push(parseInt(item.id)); + $('#tasklist').append(prepareTaskStr(item)); + changeTaskOrder(item.id); + $('#taskrow_'+item.id).effect("highlight", {color:_mtt.theme.newTaskFlashColor}, 2000); + refreshTaskCnt(); + }); + flag.tagsChanged = true; + return false; +}; + + +function changeTaskOrder(id) +{ + id = parseInt(id); + if(taskOrder.length < 2) return; + var oldOrder = taskOrder.slice(); + // sortByHand + if(curList.sort == 0) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + return taskList[a].ow-taskList[b].ow + }); + // sortByPrio + else if(curList.sort == 1) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].prio != taskList[b].prio) return taskList[b].prio-taskList[a].prio; + if(taskList[a].dueInt != taskList[b].dueInt) return taskList[a].dueInt-taskList[b].dueInt; + return taskList[a].ow-taskList[b].ow; + }); + // sortByPrio (reverse) + else if(curList.sort == 101) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].prio != taskList[b].prio) return taskList[a].prio-taskList[b].prio; + if(taskList[a].dueInt != taskList[b].dueInt) return taskList[b].dueInt-taskList[a].dueInt; + return taskList[b].ow-taskList[a].ow; + }); + // sortByDueDate + else if(curList.sort == 2) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dueInt != taskList[b].dueInt) return taskList[a].dueInt-taskList[b].dueInt; + if(taskList[a].prio != taskList[b].prio) return taskList[b].prio-taskList[a].prio; + return taskList[a].ow-taskList[b].ow; + }); + // sortByDueDate (reverse) + else if(curList.sort == 102) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dueInt != taskList[b].dueInt) return taskList[b].dueInt-taskList[a].dueInt; + if(taskList[a].prio != taskList[b].prio) return taskList[a].prio-taskList[b].prio; + return taskList[b].ow-taskList[a].ow; + }); + // sortByDateCreated + else if(curList.sort == 3) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dateInt != taskList[b].dateInt) return taskList[a].dateInt-taskList[b].dateInt; + if(taskList[a].prio != taskList[b].prio) return taskList[b].prio-taskList[a].prio; + return taskList[a].ow-taskList[b].ow; + }); + // sortByDateCreated (reverse) + else if(curList.sort == 103) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dateInt != taskList[b].dateInt) return taskList[b].dateInt-taskList[a].dateInt; + if(taskList[a].prio != taskList[b].prio) return taskList[a].prio-taskList[b].prio; + return taskList[b].ow-taskList[a].ow; + }); + // sortByDateModified + else if(curList.sort == 4) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dateEditedInt != taskList[b].dateEditedInt) return taskList[a].dateEditedInt-taskList[b].dateEditedInt; + if(taskList[a].prio != taskList[b].prio) return taskList[b].prio-taskList[a].prio; + return taskList[a].ow-taskList[b].ow; + }); + // sortByDateModified (reverse) + else if(curList.sort == 104) taskOrder.sort( function(a,b){ + if(taskList[a].compl != taskList[b].compl) return taskList[a].compl-taskList[b].compl; + if(taskList[a].dateEditedInt != taskList[b].dateEditedInt) return taskList[b].dateEditedInt-taskList[a].dateEditedInt; + if(taskList[a].prio != taskList[b].prio) return taskList[a].prio-taskList[b].prio; + return taskList[b].ow-taskList[a].ow; + }); + else return; + if(oldOrder.toString() == taskOrder.toString()) return; + if(id && taskList[id]) + { + // optimization: determine where to insert task: top or after some task + var indx = $.inArray(id,taskOrder); + if(indx ==0) { + $('#tasklist').prepend($('#taskrow_'+id)) + } else { + var after = taskOrder[indx-1]; + $('#taskrow_'+after).after($('#taskrow_'+id)); + } + } + else { + var o = $('#tasklist'); + for(var i in taskOrder) { + o.append($('#taskrow_'+taskOrder[i])); + } + } +}; + + +function prioPopup(act, el, id) +{ + if(act == 0) { + clearTimeout(objPrio.timer); + return; + } + var offset = $(el).offset(); + $('#priopopup').css({ position: 'absolute', top: offset.top + 1, left: offset.left + 1 }); + objPrio.taskId = id; + objPrio.el = el; + objPrio.timer = setTimeout("$('#priopopup').show()", 300); +}; + +function prioClick(prio, el) +{ + el.blur(); + prio = parseInt(prio); + $('#priopopup').fadeOut('fast'); //.hide(); + setTaskPrio(objPrio.taskId, prio); +}; + +function setTaskPrio(id, prio) +{ + _mtt.db.request('setPrio', {id:id, prio:prio}); + taskList[id].prio = prio; + var $t = $('#taskrow_'+id); + $t.find('.task-prio').replaceWith(preparePrio(prio, id)); + if(curList.sort != 0) changeTaskOrder(id); + $t.effect("highlight", {color:_mtt.theme.editTaskFlashColor}, 'normal'); +}; + +function setSort(v, init) +{ + $('#listmenucontainer .sort-item').removeClass('mtt-item-checked').children('.mtt-sort-direction').text(''); + if(v == 0) $('#sortByHand').addClass('mtt-item-checked'); + else if(v==1 || v==101) $('#sortByPrio').addClass('mtt-item-checked').children('.mtt-sort-direction').text(v==1 ? '↑' : '↓'); + else if(v==2 || v==102) $('#sortByDueDate').addClass('mtt-item-checked').children('.mtt-sort-direction').text(v==2 ? '↑' : '↓'); + else if(v==3 || v==103) $('#sortByDateCreated').addClass('mtt-item-checked').children('.mtt-sort-direction').text(v==3 ? '↓' : '↑'); + else if(v==4 || v==104) $('#sortByDateModified').addClass('mtt-item-checked').children('.mtt-sort-direction').text(v==4 ? '↓' : '↑'); + else return; + + curList.sort = v; + if(v == 0 && !flag.readOnly) $("#tasklist").sortable('enable'); + else $("#tasklist").sortable('disable'); + + if(!init) + { + changeTaskOrder(); + if(!flag.readOnly) _mtt.db.request('setSort', {list:curList.id, sort:curList.sort}); + } +}; + + +function changeTaskCnt(task, dir, old) +{ + if(dir > 0) dir = 1; + else if(dir < 0) dir = -1; + if(dir == 0 && old != null && task.dueClass != old.dueClass) //on saveTask + { + if(old.dueClass != '') taskCnt[old.dueClass]--; + if(task.dueClass != '') taskCnt[task.dueClass]++; + } + else if(dir == 0 && old == null) //on comleteTask + { + if(!curList.showCompl && task.compl) taskCnt.total--; + if(task.dueClass != '') taskCnt[task.dueClass] += task.compl ? -1 : 1; + } + if(dir != 0) { + if(task.dueClass != '' && !task.compl) taskCnt[task.dueClass] += dir; + taskCnt.total += dir; + } +}; + +function refreshTaskCnt() +{ + $('#cnt_total').text(taskCnt.total); + $('#cnt_past').text(taskCnt.past); + $('#cnt_today').text(taskCnt.today); + $('#cnt_soon').text(taskCnt.soon); + if(filter.due == '') $('#total').text(taskCnt.total); + else if(taskCnt[filter.due] != null) $('#total').text(taskCnt[filter.due]); +}; + + +function setTaskview(v) +{ + if(v == 0) + { + if(filter.due == '') return; + $('#taskview .btnstr').text(_mtt.lang.get('tasks')); + $('#tasklist').removeClass('filter-'+filter.due); + filter.due = ''; + $('#total').text(taskCnt.total); + } + else if(v=='past' || v=='today' || v=='soon') + { + if(filter.due == v) return; + else if(filter.due != '') { + $('#tasklist').removeClass('filter-'+filter.due); + } + $('#tasklist').addClass('filter-'+v); + $('#taskview .btnstr').text(_mtt.lang.get('f_'+v)); + $('#total').text(taskCnt[v]); + filter.due = v; + } +}; + + +function toggleAllNotes(show) +{ + for(var id in taskList) + { + if(taskList[id].note == '') continue; + if(show) $('#taskrow_'+id).addClass('task-expanded'); + else $('#taskrow_'+id).removeClass('task-expanded'); + } + curList.showNotes = show; + if(_mtt.options.saveShowNotes) _mtt.db.request('setShowNotesInList', {list:curList.id, shownotes:show}, function(json){}); +}; + + +function tabSelect(elementOrId) +{ + var id; + if(typeof elementOrId == 'number') id = elementOrId; + else if(typeof elementOrId == 'string') id = parseInt(elementOrId); + else { + id = $(elementOrId).attr('id'); + if(!id) return; + id = parseInt(id.split('_', 2)[1]); + } + if(!tabLists.exists(id)) return; + $('#lists .mtt-tabs-selected').removeClass('mtt-tabs-selected'); + $('#list_all').removeClass('mtt-tabs-selected'); + + if(id == -1) { + $('#list_all').addClass('mtt-tabs-selected').removeClass('mtt-tabs-hidden'); + $('#listmenucontainer .mtt-need-real-list').addClass('mtt-item-hidden'); + } + else { + $('#list_'+id).addClass('mtt-tabs-selected').removeClass('mtt-tabs-hidden'); + $('#listmenucontainer .mtt-need-real-list').removeClass('mtt-item-hidden'); + } + + if(curList.id != id) + { + if(id == -1) $('#mtt_body').addClass('show-all-tasks'); + else $('#mtt_body').removeClass('show-all-tasks'); + if(filter.search != '') liveSearchToggle(0, 1); + mytinytodo.doAction('listSelected', tabLists.get(id)); + } + curList = tabLists.get(id); + if(curList.hidden) { + curList.hidden = false; + if(curList.id > 0) _mtt.db.request('setHideList', {list:curList.id, hide:0}); + } + flag.tagsChanged = true; + cancelTagFilter(0, 1); + setTaskview(0); + loadTasks({clearTasklist:1}); +}; + + + +function listMenu(el) +{ + if(!mytinytodo.menus.listMenu) mytinytodo.menus.listMenu = new mttMenu('listmenucontainer', {onclick:listMenuClick}); + mytinytodo.menus.listMenu.show(el); +}; + +function listMenuClick(el, menu) +{ + if(!el.id) return; + switch(el.id) { + case 'btnAddList': addList(); break; + case 'btnRenameList': renameCurList(); break; + case 'btnDeleteList': deleteCurList(); break; + case 'btnPublish': publishCurList(); break; + case 'btnExportCSV': exportCurList('csv'); break; + case 'btnExportICAL': exportCurList('ical'); break; + case 'btnRssFeed': feedCurList(); break; + case 'btnShowCompleted': showCompletedToggle(); break; + case 'btnClearCompleted': clearCompleted(); break; + case 'sortByHand': setSort(0); break; + case 'sortByPrio': setSort(curList.sort==1 ? 101 : 1); break; + case 'sortByDueDate': setSort(curList.sort==2 ? 102 : 2); break; + case 'sortByDateCreated': setSort(curList.sort==3 ? 103 : 3); break; + case 'sortByDateModified': setSort(curList.sort==4 ? 104 : 4); break; + } +}; + +function deleteTask(id) +{ + if(!confirm(_mtt.lang.get('confirmDelete'))) { + return false; + } + _mtt.db.request('deleteTask', {id:id}, function(json){ + if(!parseInt(json.total)) return; + var item = json.list[0]; + taskOrder.splice($.inArray(id,taskOrder), 1); + $('#taskrow_'+id).fadeOut('normal', function(){ $(this).remove() }); + changeTaskCnt(taskList[id], -1); + refreshTaskCnt(); + delete taskList[id]; + }); + flag.tagsChanged = true; + return false; +}; + +function completeTask(id, ch) +{ + if(!taskList[id]) return; //click on already removed from the list while anim. effect + var compl = 0; + if(ch.checked) compl = 1; + _mtt.db.request('completeTask', {id:id, compl:compl, list:curList.id}, function(json){ + if(!parseInt(json.total)) return; + var item = json.list[0]; + if(item.compl) $('#taskrow_'+id).addClass('task-completed'); + else $('#taskrow_'+id).removeClass('task-completed'); + taskList[id] = item; + changeTaskCnt(taskList[id], 0); + if(item.compl && !curList.showCompl) { + delete taskList[id]; + taskOrder.splice($.inArray(id,taskOrder), 1); + $('#taskrow_'+id).fadeOut('normal', function(){ $(this).remove() }); + } + else if(curList.showCompl) { + $('#taskrow_'+item.id).replaceWith(prepareTaskStr(taskList[id])); + $('#taskrow_'+id).fadeOut('fast', function(){ + changeTaskOrder(id); + $(this).effect("highlight", {color:_mtt.theme.editTaskFlashColor}, 'normal', function(){$(this).css('display','')}); + }); + } + refreshTaskCnt(); + }); + return false; +}; + +function toggleTaskNote(id) +{ + var aArea = '#tasknotearea'+id; + if($(aArea).css('display') == 'none') + { + $('#notetext'+id).val(taskList[id].noteText); + $(aArea).show(); + $('#tasknote'+id).hide(); + $('#taskrow_'+id).addClass('task-expanded'); + $('#notetext'+id).focus(); + } else { + cancelTaskNote(id) + } + return false; +}; + +function cancelTaskNote(id) +{ + if(taskList[id].note == '') $('#taskrow_'+id).removeClass('task-expanded'); + $('#tasknotearea'+id).hide(); + $('#tasknote'+id).show(); + return false; +}; + +function saveTaskNote(id) +{ + _mtt.db.request('editNote', {id:id, note:$('#notetext'+id).val()}, function(json){ + if(!parseInt(json.total)) return; + var item = json.list[0]; + taskList[id].note = item.note; + taskList[id].noteText = item.noteText; + $('#tasknote'+id+'>span').html(prepareHtml(item.note)); + if(item.note == '') $('#taskrow_'+id).removeClass('task-has-note task-expanded'); + else $('#taskrow_'+id).addClass('task-has-note task-expanded'); + cancelTaskNote(id); + }); + return false; +}; + +function editTask(id) +{ + var item = taskList[id]; + if(!item) return false; + // no need to clear form + var form = document.getElementById('taskedit_form'); + form.task.value = dehtml(item.title); + form.note.value = item.noteText; + form.id.value = item.id; + form.tags.value = item.tags.split(',').join(', '); + form.duedate.value = item.duedate; + form.prio.value = item.prio; + $('#taskedit-date .date-created>span').text(item.date); + if(item.compl) $('#taskedit-date .date-completed').show().find('span').text(item.dateCompleted); + else $('#taskedit-date .date-completed').hide(); + toggleEditAllTags(0); + showEditForm(); + return false; +}; + +function clearEditForm() +{ + var form = document.getElementById('taskedit_form'); + form.task.value = ''; + form.note.value = ''; + form.tags.value = ''; + form.duedate.value = ''; + form.prio.value = '0'; + form.id.value = ''; + toggleEditAllTags(0); +}; + +function showEditForm(isAdd) +{ + var form = document.getElementById('taskedit_form'); + if(isAdd) + { + clearEditForm(); + $('#page_taskedit').removeClass('mtt-inedit').addClass('mtt-inadd'); + form.isadd.value = 1; + if(_mtt.options.autotag) form.tags.value = _mtt.filter.getTags(); + if($('#task').val() != '') + { + _mtt.db.request('parseTaskStr', { list:curList.id, title:$('#task').val(), tag:_mtt.filter.getTags() }, function(json){ + if(!json) return; + form.task.value = json.title + form.tags.value = (form.tags.value != '') ? form.tags.value +', '+ json.tags : json.tags; + form.prio.value = json.prio; + $('#task').val(''); + + }); + } + } + else { + $('#page_taskedit').removeClass('mtt-inadd').addClass('mtt-inedit'); + form.isadd.value = 0; + } + + flag.editFormChanged = false; + _mtt.pageSet('taskedit'); +}; + +function saveTask(form) +{ + if(flag.readOnly) return false; + if(form.isadd.value != 0) + return submitFullTask(form); + + _mtt.db.request('editTask', {id:form.id.value, title: form.task.value, note:form.note.value, + prio:form.prio.value, tags:form.tags.value, duedate:form.duedate.value}, + function(json){ + if(!parseInt(json.total)) return; + var item = json.list[0]; + changeTaskCnt(item, 0, taskList[item.id]); + taskList[item.id] = item; + var noteExpanded = (item.note != '' && $('#taskrow_'+item.id).is('.task-expanded')) ? 1 : 0; + $('#taskrow_'+item.id).replaceWith(prepareTaskStr(item, noteExpanded)); + if(curList.sort != 0) changeTaskOrder(item.id); + _mtt.pageBack(); //back to list + refreshTaskCnt(); + $('#taskrow_'+item.id).effect("highlight", {color:_mtt.theme.editTaskFlashColor}, 'normal', function(){$(this).css('display','')}); + }); + $("#edittags").flushCache(); + flag.tagsChanged = true; + return false; +}; + +function toggleEditAllTags(show) +{ + if(show) + { + if(curList.id == -1) { + var taskId = document.getElementById('taskedit_form').id.value; + loadTags(taskList[taskId].listId, fillEditAllTags); + } + else if(flag.tagsChanged) loadTags(curList.id, fillEditAllTags); + else fillEditAllTags(); + showhide($('#alltags_hide'), $('#alltags_show')); + } + else { + $('#alltags').hide(); + showhide($('#alltags_show'), $('#alltags_hide')) + } +}; + +function fillEditAllTags() +{ + var a = []; + for(var i=tagsList.length-1; i>=0; i--) { + a.push(''+tagsList[i].tag+''); + } + $('#alltags .tags-list').html(a.join(', ')); + $('#alltags').show(); +}; + +function addEditTag(tag) +{ + var v = $('#edittags').val(); + if(v == '') { + $('#edittags').val(tag); + return; + } + var r = v.search(new RegExp('(^|,)\\s*'+tag+'\\s*(,|$)')); + if(r < 0) $('#edittags').val(v+', '+tag); +}; + +function loadTags(listId, callback) +{ + _mtt.db.request('tagCloud', {list:listId}, function(json){ + if(!parseInt(json.total)) tagsList = []; + else tagsList = json.cloud; + var cloud = ''; + $.each(tagsList, function(i,item){ + cloud += ' '+item.tag+''; + }); + $('#tagcloudcontent').html(cloud) + flag.tagsChanged = false; + callback(); + }); +}; + +function cancelTagFilter(tagId, dontLoadTasks) +{ + if(tagId) _mtt.filter.cancelTag(tagId); + else _mtt.filter.clear(); + if(dontLoadTasks==null || !dontLoadTasks) loadTasks(); +}; + +function addFilterTag(tag, tagId, exclude) +{ + if(!_mtt.filter.addTag(tagId, tag, exclude)) return false; + loadTasks(); +}; + +function liveSearchToggle(toSearch, dontLoad) +{ + if(toSearch) + { + $('#search').focus(); + } + else + { + if($('#search').val() != '') { + filter.search = ''; + $('#search').val(''); + $('#searchbarkeyword').text(''); + $('#searchbar').hide(); + $('#search_close').hide(); + if(!dontLoad) loadTasks(); + } + + $('#search').blur(); + } +}; + +function searchTasks(force) +{ + var newkeyword = $('#search').val(); + if(newkeyword == filter.search && !force) return false; + filter.search = newkeyword; + $('#searchbarkeyword').text(filter.search); + if(filter.search != '') $('#searchbar').fadeIn('fast'); + else $('#searchbar').fadeOut('fast'); + loadTasks(); + return false; +}; + + +function submitFullTask(form) +{ + if(flag.readOnly) return false; + + _mtt.db.request('fullNewTask', { list:curList.id, tag:_mtt.filter.getTags(), title: form.task.value, note:form.note.value, + prio:form.prio.value, tags:form.tags.value, duedate:form.duedate.value }, function(json){ + if(!parseInt(json.total)) return; + form.task.value = ''; + var item = json.list[0]; + taskList[item.id] = item; + taskOrder.push(parseInt(item.id)); + $('#tasklist').append(prepareTaskStr(item)); + changeTaskOrder(item.id); + _mtt.pageBack(); + $('#taskrow_'+item.id).effect("highlight", {color:_mtt.theme.newTaskFlashColor}, 2000); + changeTaskCnt(item, 1); + refreshTaskCnt(); + }); + + $("#edittags").flushCache(); + flag.tagsChanged = true; + return false; +}; + + +function sortStart(event,ui) +{ + // remember initial order before sorting + sortOrder = $(this).sortable('toArray'); +}; + +function orderChanged(event,ui) +{ + if(!ui.item[0]) return; + var itemId = ui.item[0].id; + var n = $(this).sortable('toArray'); + + // remove possible empty id's + for(var i=0; iposition + var h0 = {}; //before + for(var j=0; j $(window).width()) + this.$container.width($(window).width() - (this.$container.outerWidth(true) - this.$container.width())); + + $caller.addClass('mtt-menu-button-active'); + var offset = $caller.offset(); + var x2 = $(window).width() + $(document).scrollLeft() - this.$container.outerWidth(true) - 1; + var x = offset.left < x2 ? offset.left : x2; + if(x<0) x=0; + var y = offset.top+caller.offsetHeight-1; + if(y + this.$container.outerHeight(true) > $(window).height() + $(document).scrollTop()) y = offset.top - this.$container.outerHeight(); + if(y<0) y=0; + this.$container.css({ position: 'absolute', top: y, left: x, width:this.$container.width() /*, 'min-width': $caller.width()*/ }).show(); + var menu = this; + $(document).bind('mousedown.mttmenuclose', function(e){ menu.close(e) }); + this.menuOpen = true; + }; + + this.showSub = function() + { + this.$caller.addClass('mtt-menu-item-active'); + var offset = this.$caller.offset(); + var x = offset.left+this.$caller.outerWidth(); + if(x + this.$container.outerWidth(true) > $(window).width() + $(document).scrollLeft()) x = offset.left - this.$container.outerWidth() - 1; + if(x<0) x=0; + var y = offset.top + this.parent.$container.offset().top-this.parent.$container.find('li:first').offset().top; + if(y + this.$container.outerHeight(true) > $(window).height() + $(document).scrollTop()) y = $(window).height() + $(document).scrollTop()- this.$container.outerHeight(true) - 1; + if(y<0) y=0; + this.$container.css({ position: 'absolute', top: y, left: x, width:this.$container.width() /*, 'min-width': this.$caller.outerWidth()*/ }).show(); + this.menuOpen = true; + }; + + this.destroy = function() + { + for(var i in this.submenu) { + this.submenu[i].destroy(); + delete this.submenu[i]; + } + this.$container.find('li').unbind(); //'click mouseenter mouseleave' + }; +}; + + +function taskContextMenu(el, id) +{ + if(!_mtt.menus.cmenu) _mtt.menus.cmenu = new mttMenu('taskcontextcontainer', { + onclick: taskContextClick, + beforeShow: function() { + $('#cmenupriocontainer li').removeClass('mtt-item-checked'); + $('#cmenu_prio\\:'+ taskList[_mtt.menus.cmenu.tag].prio).addClass('mtt-item-checked'); + } + }); + _mtt.menus.cmenu.tag = id; + _mtt.menus.cmenu.show(el); +}; + +function taskContextClick(el, menu) +{ + if(!el.id) return; + var taskId = parseInt(_mtt.menus.cmenu.tag); + var id = el.id, value; + var a = id.split(':'); + if(a.length == 2) { + id = a[0]; + value = a[1]; + } + switch(id) { + case 'cmenu_edit': editTask(taskId); break; + case 'cmenu_note': toggleTaskNote(taskId); break; + case 'cmenu_delete': deleteTask(taskId); break; + case 'cmenu_prio': setTaskPrio(taskId, parseInt(value)); break; + case 'cmenu_list': + if(menu.$caller && menu.$caller.attr('id')=='cmenu_move') moveTaskToList(taskId, value); + break; + } +}; + + +function moveTaskToList(taskId, listId) +{ + if(curList.id == listId) return; + _mtt.db.request('moveTask', {id:taskId, from:curList.id, to:listId}, function(json){ + if(!parseInt(json.total)) return; + if(curList.id == -1) + { + // leave the task in current tab (all tasks tab) + var item = json.list[0]; + changeTaskCnt(item, 0, taskList[item.id]); + taskList[item.id] = item; + var noteExpanded = (item.note != '' && $('#taskrow_'+item.id).is('.task-expanded')) ? 1 : 0; + $('#taskrow_'+item.id).replaceWith(prepareTaskStr(item, noteExpanded)); + if(curList.sort != 0) changeTaskOrder(item.id); + refreshTaskCnt(); + $('#taskrow_'+item.id).effect("highlight", {color:_mtt.theme.editTaskFlashColor}, 'normal', function(){$(this).css('display','')}); + } + else { + // remove the task from currrent tab + changeTaskCnt(taskList[taskId], -1) + delete taskList[taskId]; + taskOrder.splice($.inArray(taskId,taskOrder), 1); + $('#taskrow_'+taskId).fadeOut('normal', function(){ $(this).remove() }); + refreshTaskCnt(); + } + }); + + $("#edittags").flushCache(); + flag.tagsChanged = true; +}; + + +function cmenuOnListsLoaded() +{ + if(_mtt.menus.cmenu) _mtt.menus.cmenu.destroy(); + _mtt.menus.cmenu = null; + var s = ''; + var all = tabLists.getAll(); + for(var i in all) { + s += '
    • '+all[i].name+'
    • '; + } + $('#cmenulistscontainer ul').html(s); +}; + +function cmenuOnListAdded(list) +{ + if(_mtt.menus.cmenu) _mtt.menus.cmenu.destroy(); + _mtt.menus.cmenu = null; + $('#cmenulistscontainer ul').append('
    • '+list.name+'
    • '); +}; + +function cmenuOnListRenamed(list) +{ + $('#cmenu_list\\:'+list.id).text(list.name); +}; + +function cmenuOnListSelected(list) +{ + $('#cmenulistscontainer li').removeClass('mtt-item-disabled'); + $('#cmenu_list\\:'+list.id).addClass('mtt-item-disabled').removeClass('mtt-list-hidden'); +}; + +function cmenuOnListOrderChanged() +{ + cmenuOnListsLoaded(); + $('#cmenu_list\\:'+curList.id).addClass('mtt-item-disabled'); +}; + +function cmenuOnListHidden(list) +{ + $('#cmenu_list\\:'+list.id).addClass('mtt-list-hidden'); +}; + + +function tabmenuOnListSelected(list) +{ + if(list.published) { + $('#btnPublish').addClass('mtt-item-checked'); + $('#btnRssFeed').removeClass('mtt-item-disabled'); + } + else { + $('#btnPublish').removeClass('mtt-item-checked'); + $('#btnRssFeed').addClass('mtt-item-disabled'); + } + if(list.showCompl) $('#btnShowCompleted').addClass('mtt-item-checked'); + else $('#btnShowCompleted').removeClass('mtt-item-checked'); +}; + + +function listOrderChanged(event, ui) +{ + var a = $(this).sortable("toArray"); + var order = []; + for(var i in a) { + order.push(a[i].split('_')[1]); + } + tabLists.reorder(order); + _mtt.db.request('changeListOrder', {order:order}); + _mtt.doAction('listOrderChanged', {order:order}); +}; + +function showCompletedToggle() +{ + var act = curList.showCompl ? 0 : 1; + curList.showCompl = tabLists.get(curList.id).showCompl = act; + if(act) $('#btnShowCompleted').addClass('mtt-item-checked'); + else $('#btnShowCompleted').removeClass('mtt-item-checked'); + loadTasks({setCompl:1}); +}; + +function clearCompleted() +{ + if(!curList) return false; + var r = confirm(_mtt.lang.get('clearCompleted')); + if(!r) return; + _mtt.db.request('clearCompletedInList', {list:curList.id}, function(json){ + if(!parseInt(json.total)) return; + flag.tagsChanged = true; + if(curList.showCompl) loadTasks(); + }); +}; + +function tasklistClick(e) +{ + var node = e.target.nodeName.toUpperCase(); + if(node=='SPAN' || node=='LI' || node=='DIV') + { + var li = findParentNode(e.target, 'LI'); + if(li) { + if(selTask && li.id != selTask) $('#'+selTask).removeClass('clicked doubleclicked'); + selTask = li.id; + if($(li).is('.clicked')) $(li).toggleClass('doubleclicked'); + else $(li).addClass('clicked'); + } + } +}; + + +function showhide(a,b) +{ + a.show(); + b.hide(); +}; + +function findParentNode(el, node) +{ + // in html nodename is in uppercase, in xhtml nodename in in lowercase + if(el.nodeName.toUpperCase() == node) return el; + if(!el.parentNode) return null; + while(el.parentNode) { + el = el.parentNode; + if(el.nodeName.toUpperCase() == node) return el; + } +}; + +function getLiTaskId(el) +{ + var li = findParentNode(el, 'LI'); + if(!li || !li.id) return 0; + return li.id.split('_',2)[1]; +}; + +function isParentId(el, id) +{ + if(el.id && $.inArray(el.id, id) != -1) return true; + if(!el.parentNode) return null; + return isParentId(el.parentNode, id); +}; + +function dehtml(str) +{ + return str.replace(/"/g,'"').replace(/</g,'<').replace(/>/g,'>').replace(/&/g,'&'); +}; + + +function slmenuOnListsLoaded() +{ + if(_mtt.menus.selectlist) { + _mtt.menus.selectlist.destroy(); + _mtt.menus.selectlist = null; + } + + var s = ''; + var all = tabLists.getAll(); + for(var i in all) { + s += '
    • '+all[i].name+'
    • '; + } + $('#slmenucontainer ul>.slmenu-lists-begin').nextAll().remove(); + $('#slmenucontainer ul>.slmenu-lists-begin').after(s); +}; + +function slmenuOnListRenamed(list) +{ + $('#slmenucontainer li.list-id-'+list.id).find('a').html(list.name); +}; + +function slmenuOnListAdded(list) +{ + if(_mtt.menus.selectlist) { + _mtt.menus.selectlist.destroy(); + _mtt.menus.selectlist = null; + } + $('#slmenucontainer ul').append('
    • '+list.name+'
    • '); +}; + +function slmenuOnListSelected(list) +{ + $('#slmenucontainer li').removeClass('mtt-item-checked'); + $('#slmenucontainer li.list-id-'+list.id).addClass('mtt-item-checked').removeClass('mtt-list-hidden'); + +}; + +function slmenuOnListHidden(list) +{ + $('#slmenucontainer li.list-id-'+list.id).addClass('mtt-list-hidden'); +}; + +function slmenuSelect(el, menu) +{ + if(!el.id) return; + var id = el.id, value; + var a = id.split(':'); + if(a.length == 2) { + id = a[0]; + value = a[1]; + } + if(id == 'slmenu_list') { + tabSelect(parseInt(value)); + } + return false; +}; + + +function exportCurList(format) +{ + if(!curList) return; + if(!format.match(/^[a-z0-9-]+$/i)) return; + window.location.href = _mtt.mttUrl + 'export.php?list='+curList.id +'&format='+format; +}; + +function feedCurList() +{ + if(!curList) return; + window.location.href = _mtt.mttUrl + 'feed.php?list='+curList.id; +} + +function hideTab(listId) +{ + if(typeof listId != 'number') { + var id = $(listId).attr('id'); + if(!id) return; + listId = parseInt(id.split('_', 2)[1]); + } + + if(!tabLists.get(listId)) return false; + + // if we hide current tab + var listIdToSelect = 0; + if(curList.id == listId) { + var all = tabLists.getAll(); + for(var i in all) { + if(all[i].id != curList.id && !all[i].hidden) { + listIdToSelect = all[i].id; + break; + } + } + // do not hide the tab if others are hidden + if(!listIdToSelect) return false; + } + + if(listId == -1) { + $('#list_all').addClass('mtt-tabs-hidden').removeClass('mtt-tabs-selected'); + } + else { + $('#list_'+listId).addClass('mtt-tabs-hidden').removeClass('mtt-tabs-selected'); + } + + tabLists.get(listId).hidden = true; + + if(listId > 0) { + _mtt.db.request('setHideList', {list:listId, hide:1}); + _mtt.doAction('listHidden', tabLists.get(listId)); + } + + if(listIdToSelect) { + tabSelect(listIdToSelect); + } +} + +/* + Errors and Info messages +*/ + +function flashError(str, details) +{ + $("#msg>.msg-text").text(str) + $("#msg>.msg-details").text(details); + $("#loading").hide(); + $("#msg").addClass('mtt-error').effect("highlight", {color:_mtt.theme.msgFlashColor}, 700); +} + +function flashInfo(str, details) +{ + $("#msg>.msg-text").text(str) + $("#msg>.msg-details").text(details); + $("#loading").hide(); + $("#msg").addClass('mtt-info').effect("highlight", {color:_mtt.theme.msgFlashColor}, 700); +} + +function toggleMsgDetails() +{ + var el = $("#msg>.msg-details"); + if(!el) return; + if(el.css('display') == 'none') el.show(); + else el.hide() +} + + +/* + Authorization +*/ +function updateAccessStatus() +{ + // flag.needAuth is not changed after pageload + if(flag.needAuth) + { + $('#bar_auth').show(); + if(flag.isLogged) { + showhide($("#bar_logout"),$("#bar_login")); + $('#bar .menu-owner').show(); + $('#bar .bar-delim').show(); + } + else { + showhide($("#bar_login"),$("#bar_logout")); + $('#bar .menu-owner').hide(); + $('#bar .bar-delim').hide(); + } + } + else { + $('#bar .menu-owner').show(); + } + if(flag.needAuth && !flag.isLogged) { + flag.readOnly = true; + $("#bar_public").show(); + $('#mtt_body').addClass('readonly') + liveSearchToggle(1); + // remove some tab menu items + $('#btnRenameList,#btnDeleteList,#btnClearCompleted,#btnPublish').remove(); + } + else { + flag.readOnly = false; + $('#mtt_body').removeClass('readonly') + $("#bar_public").hide(); + liveSearchToggle(0); + } + $('#page_ajax').hide(); +} + +function showAuth(el) +{ + var w = $('#authform'); + if(w.css('display') == 'none') + { + var offset = $(el).offset(); + w.css({ + position: 'absolute', + top: offset.top + el.offsetHeight + 3, + left: offset.left + el.offsetWidth - w.outerWidth() + }).show(); + $('#password').focus(); + } + else { + w.hide(); + el.blur(); + } +} + +function doAuth(form) +{ + $.post(mytinytodo.mttUrl+'ajax.php?login', { login:1, password: form.password.value }, function(json){ + form.password.value = ''; + if(json.logged) + { + flag.isLogged = true; + window.location.reload(); + } + else { + flashError(_mtt.lang.get('invalidpass')); + $('#password').focus(); + } + }, 'json'); + $('#authform').hide(); +} + +function logout() +{ + $.post(mytinytodo.mttUrl+'ajax.php?logout', { logout:1 }, function(json){ + flag.isLogged = false; + window.location.reload(); + }, 'json'); + return false; +} + + +/* + Settings +*/ + +function showSettings() +{ + if(_mtt.pages.current.page == 'ajax' && _mtt.pages.current.pageClass == 'settings') return false; + $('#page_ajax').load(_mtt.mttUrl+'settings.php?ajax=yes',null,function(){ + //showhide($('#page_ajax').addClass('mtt-page-settings'), $('#page_tasks')); + _mtt.pageSet('ajax','settings'); + }) + return false; +} + +function saveSettings(frm) +{ + if(!frm) return false; + var params = { save:'ajax' }; + $(frm).find("input:text,input:password,input:checked,select").filter(":enabled").each(function() { params[this.name || '__'] = this.value; }); + $(frm).find(":submit").attr('disabled','disabled').blur(); + $.post(_mtt.mttUrl+'settings.php', params, function(json){ + if(json.saved) { + flashInfo(_mtt.lang.get('settingsSaved')); + setTimeout('window.location.reload();', 1000); + } + }, 'json'); +} + +})(); \ No newline at end of file diff --git a/sources/www/mytinytodo_ajax_storage.js b/sources/www/mytinytodo_ajax_storage.js new file mode 100644 index 0000000..7600a7f --- /dev/null +++ b/sources/www/mytinytodo_ajax_storage.js @@ -0,0 +1,178 @@ +/* + This file is a part of myTinyTodo. + (C) Copyright 2010 Max Pozdeev + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +// AJAX myTinyTodo Storage + +(function(){ + +var mtt; + +function mytinytodoStorageAjax(amtt) +{ + this.mtt = mtt = amtt; +} + +window.mytinytodoStorageAjax = mytinytodoStorageAjax; + +mytinytodoStorageAjax.prototype = +{ + /* required method */ + request:function(action, params, callback) + { + if(!this[action]) throw "Unknown storage action: "+action; + + this[action](params, function(json){ + if(json.denied) mtt.errorDenied(); + if(callback) callback.call(mtt, json) + }); + }, + + + loadLists: function(params, callback) + { + $.getJSON(this.mtt.mttUrl+'ajax.php?loadLists'+'&rnd='+Math.random(), callback); + }, + + + loadTasks: function(params, callback) + { + var q = ''; + if(params.search && params.search != '') q += '&s='+encodeURIComponent(params.search); + if(params.tag && params.tag != '') q += '&t='+encodeURIComponent(params.tag); + if(params.setCompl && params.setCompl != 0) q += '&setCompl=1'; + q += '&rnd='+Math.random(); + +/* $.getJSON(mtt.mttUrl+'ajax.php?loadTasks&list='+params.list+'&compl='+params.compl+'&sort='+params.sort+'&tz='+params.tz+q, function(json){ + callback.call(mtt, json); + }) +*/ + + $.getJSON(this.mtt.mttUrl+'ajax.php?loadTasks&list='+params.list+'&compl='+params.compl+'&sort='+params.sort+q, callback); + }, + + + newTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?newTask', + { list:params.list, title: params.title, tag:params.tag }, callback, 'json'); + }, + + + fullNewTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?fullNewTask', + { list:params.list, title:params.title, note:params.note, prio:params.prio, tags:params.tags, duedate:params.duedate }, + callback, 'json'); + }, + + + editTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?editTask='+params.id, + { id:params.id, title:params.title, note:params.note, prio:params.prio, tags:params.tags, duedate:params.duedate }, + callback, 'json'); + }, + + + editNote: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?editNote='+params.id, {id:params.id, note: params.note}, callback, 'json'); + }, + + + completeTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?completeTask='+params.id, { id:params.id, compl:params.compl }, callback, 'json'); + }, + + + deleteTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?deleteTask='+params.id, { id:params.id }, callback, 'json'); + }, + + + setPrio: function(params, callback) + { + $.getJSON(this.mtt.mttUrl+'ajax.php?setPrio='+params.id+'&prio='+params.prio+'&rnd='+Math.random(), callback); + }, + + + setSort: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?setSort', { list:params.list, sort:params.sort }, callback, 'json'); + }, + + changeOrder: function(params, callback) + { + var order = ''; + for(var i in params.order) { + order += params.order[i].id +'='+ params.order[i].diff + '&'; + } + $.post(this.mtt.mttUrl+'ajax.php?changeOrder', { order:order }, callback, 'json'); + }, + + tagCloud: function(params, callback) + { + $.getJSON(this.mtt.mttUrl+'ajax.php?tagCloud&list='+params.list+'&rnd='+Math.random(), callback); + }, + + moveTask: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?moveTask', { id:params.id, from:params.from, to:params.to }, callback, 'json'); + }, + + parseTaskStr: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?parseTaskStr', { list:params.list, title:params.title, tag:params.tag }, callback, 'json'); + }, + + + // Lists + addList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?addList', { name:params.name }, callback, 'json'); + + }, + + renameList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?renameList', { list:params.list, name:params.name }, callback, 'json'); + }, + + deleteList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?deleteList', { list:params.list }, callback, 'json'); + }, + + publishList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?publishList', { list:params.list, publish:params.publish }, callback, 'json'); + }, + + setShowNotesInList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?setShowNotesInList', { list:params.list, shownotes:params.shownotes }, callback, 'json'); + }, + + setHideList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?setHideList', { list:params.list, hide:params.hide }, callback, 'json'); + }, + + changeListOrder: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?changeListOrder', { order:params.order }, callback, 'json'); + }, + + clearCompletedInList: function(params, callback) + { + $.post(this.mtt.mttUrl+'ajax.php?clearCompletedInList', { list:params.list }, callback, 'json'); + } + +}; + +})(); \ No newline at end of file diff --git a/sources/www/mytinytodo_lang.php b/sources/www/mytinytodo_lang.php new file mode 100644 index 0000000..08c3797 --- /dev/null +++ b/sources/www/mytinytodo_lang.php @@ -0,0 +1,12 @@ +makeJS() .");"; + +?> \ No newline at end of file diff --git a/sources/www/settings.php b/sources/www/settings.php new file mode 100644 index 0000000..6bb51b0 --- /dev/null +++ b/sources/www/settings.php @@ -0,0 +1,260 @@ + + Licensed under the GNU GPL v2 license. See file COPYRIGHT for details. +*/ + +require_once('./init.php'); + +$lang = Lang::instance(); + +if($needAuth && !is_logged()) +{ + die("Access denied!
      Disable password protection or Log in."); +} + +if(isset($_POST['save'])) +{ + stop_gpc($_POST); + $t = array(); + $langs = getLangs(); + Config::$params['lang']['options'] = array_keys($langs); + Config::set('lang', _post('lang')); + + // in Demo mode we can set only language by cookies + if(defined('MTTDEMO')) { + setcookie('lang', Config::get('lang'), 0, url_dir(Config::get('url')=='' ? $_SERVER['REQUEST_URI'] : Config::get('url'))); + $t['saved'] = 1; + jsonExit($t); + } + + if(isset($_POST['password']) && $_POST['password'] != '') Config::set('password', $_POST['password']); + elseif(!_post('allowpassword')) Config::set('password', ''); + Config::set('smartsyntax', (int)_post('smartsyntax')); + // Do not set invalid timezone + try { + $tz = trim(_post('timezone')); + $testTZ = new DateTimeZone($tz); //will throw Exception on invalid timezone + Config::set('timezone', $tz); + } + catch (Exception $e) { + } + Config::set('autotag', (int)_post('autotag')); + Config::set('session', _post('session')); + Config::set('firstdayofweek', (int)_post('firstdayofweek')); + Config::set('clock', (int)_post('clock')); + Config::set('dateformat', _post('dateformat')); + Config::set('dateformat2', _post('dateformat2')); + Config::set('dateformatshort', _post('dateformatshort')); + Config::set('title', trim(_post('title'))); + Config::set('showdate', (int)_post('showdate')); + Config::save(); + $t['saved'] = 1; + jsonExit($t); +} + + +function _c($key) +{ + return Config::get($key); +} + +function getLangs($withContents = 0) +{ + if (!$h = opendir(MTTPATH. 'lang')) return false; + $a = array(); + while(false !== ($file = readdir($h))) + { + if(preg_match('/(.+)\.php$/', $file, $m) && $file != 'class.default.php') { + $a[$m[1]] = $m[1]; + if($withContents) { + $a[$m[1]] = getLangDetails(MTTPATH. 'lang'. DIRECTORY_SEPARATOR. $file, $m[1]); + $a[$m[1]]['name'] = $a[$m[1]]['original_name']; + $a[$m[1]]['title'] = $a[$m[1]]['language']; + } + } + } + closedir($h); + return $a; +} + +function getLangDetails($filename, $default) +{ + $contents = file_get_contents($filename); + $a = array('language'=>$default, 'original_name'=>$default); + if(preg_match("|/\\*\s*myTinyTodo language pack([\s\S]+?)\\*/|", $contents, $m)) + { + $str = $m[1]; + if(preg_match("|Language\s*:\s*(.+)|i", $str, $m)) { + $a['language'] = trim($m[1]); + } + if(preg_match("|Original name\s*:\s*(.+)|i", $str, $m)) { + $a['original_name'] = trim($m[1]); + } + } + return $a; +} + +function selectOptions($a, $value, $default=null) +{ + if(!$a) return ''; + $s = ''; + if($default !== null && !isset($a[$value])) $value = $default; + foreach($a as $k=>$v) { + $s .= ''; + } + return $s; +} + +/* + @param array $a array of id=>array(name, optional title) + @param mixed $key Key of OPTION to be selected + @param mixed $default Default key if $key is not present in $a +*/ +function selectOptionsA($a, $key, $default=null) +{ + if(!$a) return ''; + $s = ''; + if($default !== null && !isset($a[$key])) $key = $default; + foreach($a as $k=>$v) { + $s .= ''; + } + return $s; +} + +function timezoneIdentifiers() +{ + $zones = DateTimeZone::listIdentifiers(); + $a = array(); + foreach($zones as $v) { + $a[$v] = $v; + } + return $a; +} + +header('Content-type:text/html; charset=utf-8'); +?> + +
      + +

      + + + +
      + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
      :
      :
      : +
      +
      +
      :
      />
      :
      +
      + +
      :
      +
      + +
      : +
      + (<mytinytodo_dir>/tmp/sessions) +
      : + +
      : + +
      : + + +
      : + + +
      : + + +
      : + +
      : +
      + +
      + + + + +
      + +
      \ No newline at end of file diff --git a/sources/www/themes/default/images/COPYRIGHT b/sources/www/themes/default/images/COPYRIGHT new file mode 100644 index 0000000..0e134e5 --- /dev/null +++ b/sources/www/themes/default/images/COPYRIGHT @@ -0,0 +1,13 @@ +Image files page_white_text.png and calendar.png and some icons in buttons.png +are (or based on) icons from Silk Icons set by Mark James (http://www.famfamfam.com/lab/icons/silk/), +licensed under the Creative Commons Attribution 2.5 License (http://creativecommons.org/licenses/by/2.5/). + +Some icons in buttons.png are based on "Silk Companion 1" icons set by Damien Guard +(http://damieng.com/creative/icons/silk-companion-1-icons), licensed under the + Creative Commons Attribution 2.5 License (http://creativecommons.org/licenses/by/2.5/). + +Icons in mzl.png are (or based on) icons from Mozilla Source Code, +(http://www.mozilla.org/MPL/#source-code), licensed under the terms +of tri-license (MPL 1.1/GPL 2.0/LGPL 2.1). + +Other images in this directory were made by Max Pozdeev and licensed under the terms of GNU GPL v2+. \ No newline at end of file diff --git a/sources/www/themes/default/images/arrdown.gif b/sources/www/themes/default/images/arrdown.gif new file mode 100644 index 0000000..8ea51d9 Binary files /dev/null and b/sources/www/themes/default/images/arrdown.gif differ diff --git a/sources/www/themes/default/images/arrdown2.gif b/sources/www/themes/default/images/arrdown2.gif new file mode 100644 index 0000000..5934ee4 Binary files /dev/null and b/sources/www/themes/default/images/arrdown2.gif differ diff --git a/sources/www/themes/default/images/buttons.png b/sources/www/themes/default/images/buttons.png new file mode 100755 index 0000000..68763d4 Binary files /dev/null and b/sources/www/themes/default/images/buttons.png differ diff --git a/sources/www/themes/default/images/calendar.png b/sources/www/themes/default/images/calendar.png new file mode 100644 index 0000000..6589138 Binary files /dev/null and b/sources/www/themes/default/images/calendar.png differ diff --git a/sources/www/themes/default/images/closetag.gif b/sources/www/themes/default/images/closetag.gif new file mode 100644 index 0000000..bfea142 Binary files /dev/null and b/sources/www/themes/default/images/closetag.gif differ diff --git a/sources/www/themes/default/images/corner_left.gif b/sources/www/themes/default/images/corner_left.gif new file mode 100644 index 0000000..f01063a Binary files /dev/null and b/sources/www/themes/default/images/corner_left.gif differ diff --git a/sources/www/themes/default/images/corner_right.gif b/sources/www/themes/default/images/corner_right.gif new file mode 100644 index 0000000..1619019 Binary files /dev/null and b/sources/www/themes/default/images/corner_right.gif differ diff --git a/sources/www/themes/default/images/icons.gif b/sources/www/themes/default/images/icons.gif new file mode 100644 index 0000000..84e18e0 Binary files /dev/null and b/sources/www/themes/default/images/icons.gif differ diff --git a/sources/www/themes/default/images/index.html b/sources/www/themes/default/images/index.html new file mode 100644 index 0000000..fdb6456 --- /dev/null +++ b/sources/www/themes/default/images/index.html @@ -0,0 +1 @@ +Place for Images \ No newline at end of file diff --git a/sources/www/themes/default/images/loading1.gif b/sources/www/themes/default/images/loading1.gif new file mode 100644 index 0000000..7525a26 Binary files /dev/null and b/sources/www/themes/default/images/loading1.gif differ diff --git a/sources/www/themes/default/images/loading1_24.gif b/sources/www/themes/default/images/loading1_24.gif new file mode 100644 index 0000000..7d7dbbc Binary files /dev/null and b/sources/www/themes/default/images/loading1_24.gif differ diff --git a/sources/www/themes/default/images/mzl.png b/sources/www/themes/default/images/mzl.png new file mode 100755 index 0000000..2707c97 Binary files /dev/null and b/sources/www/themes/default/images/mzl.png differ diff --git a/sources/www/themes/default/images/page_white_text.png b/sources/www/themes/default/images/page_white_text.png new file mode 100644 index 0000000..813f712 Binary files /dev/null and b/sources/www/themes/default/images/page_white_text.png differ diff --git a/sources/www/themes/default/images/tab_hover.gif b/sources/www/themes/default/images/tab_hover.gif new file mode 100644 index 0000000..170362d Binary files /dev/null and b/sources/www/themes/default/images/tab_hover.gif differ diff --git a/sources/www/themes/default/index.php b/sources/www/themes/default/index.php new file mode 100644 index 0000000..4d0161e --- /dev/null +++ b/sources/www/themes/default/index.php @@ -0,0 +1,288 @@ + + + + + +<?php mttinfo('title'); ?> + + + + + + + + + + + + + + + + + + + + + + + +
      +
      +
      + +

      + +
      + +
      +
      +
      + + + + + + + +
      +
      + +
      + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
      +
      +
      + + + +
      + + \ No newline at end of file diff --git a/sources/www/themes/default/pda.css b/sources/www/themes/default/pda.css new file mode 100644 index 0000000..95d7fe3 --- /dev/null +++ b/sources/www/themes/default/pda.css @@ -0,0 +1,50 @@ +body { margin:0px; font-size:100%; } +h2 { margin:0; margin-bottom:2px; font-size:1em; } +h3 { margin-bottom:4px; padding:4px 0; } +#body { margin-left:1px; margin-right:1px; padding:1px; padding-bottom:12px;} +#bar_login, #bar_logout { padding-right:1px; } + +#tabs ul { margin-top:0px; } +#tabs ul li { width:70px; margin-right: 1px; } +.tab-content { padding:4px; } + +#htab_search { width:40%; max-width:190px; } +.mtt-searchbox { float:right; } +.mtt-searchbox td { width:40%; } +#toolbar.mtt-intask #htab_search { display:none; } +#toolbar.mtt-insearch #htab_newtask { display:none; } +#toolbar.mtt-insearch #htab_search { width:100%; } +#toolbar.mtt-insearch .mtt-searchbox td { width:40%; } + +#tasklist li { padding:0.5em 3px; overflow:hidden; } +.task-actions { display:none; } +.task-date { display:none; } +.task-note-actions { display:block; padding-top:8px; } +.task-note-block { margin-left:0px; border-left:1px solid #777777; background:none; padding-left:4px; margin-top:1px; padding-top:0px; display:none; } +.task-note-area textarea { width:95%; } +.task-middle { margin-right:0px; } + +#tasklist li .task-through { white-space:nowrap; overflow:hidden; } +#tasklist li:hover { background-color:#ffffff; } +#tasklist li.task-expanded .task-note-block { display:none; } +/*#tasklist li.task-expanded .task-toggle { background-position:-32px 0; }*/ +#tasklist li.clicked { background-color:#f6f6f6; } +#tasklist li.clicked .task-actions { display:block; } +#tasklist li.clicked .task-through { white-space:normal; display:inline; } +#tasklist li.clicked.task-has-note .task-note-block { display:block; } +/*#tasklist li.clicked.task-has-note .task-toggle { background-position:-48px 0; } */ +#tasklist li.clicked.doubleclicked.task-has-note .task-note-block { display:none; } +.task-toggle { display:none; } +.task-middle { margin-left:25px; } + +#page_taskedit { max-width:99.5%; border:none; position:static; padding:0; } +#page_taskedit .form-table { width:100%; } +#page_taskedit .form-row .in500 { color:#444444; } +#page_taskedit .form-row textarea { height: 70px; } + +#loading { padding:0px; padding-top:1px; padding-right:1px; height:16px; overflow:hidden; } +#loading img { /*width:8px; height:8px;*/ } + +#tagcloud { max-width:100%; } +.mtt-settings-table .in350 { min-width:50px; } +.mtt-notes-showhide { display:none; } diff --git a/sources/www/themes/default/print.css b/sources/www/themes/default/print.css new file mode 100644 index 0000000..a55df63 --- /dev/null +++ b/sources/www/themes/default/print.css @@ -0,0 +1,31 @@ +html { height:0; } +body { height:0; min-height:0; margin:0; } +h2{ display: none; } +h3 { border-bottom:2px solid #777777; } +#lists { display: none; } +#toolbar { display: none; } +.small-bar { display:none; } +.task-actions { display:none; } + +#bar { display:none; } +#taskviewcontainer { border:none; } +#taskviewcontainer img { display:none; } + +#tasklist { list-style-type: decimal; list-style-position: outside; } +#tasklist li { padding-left:0px; margin-left:30px; border-bottom:none; padding-bottom: 8px; } +div.task-note-block { border-left:1px solid #777777; background:none; padding-left:5px; margin-top:5px; padding-top:0px; font-size:9pt; color:#333333; } +.task-middle { margin-left:0px; margin-right:3px; } +.task-left { display:none; } + +.task-date { white-space:nowrap; margin-left:10px; } +#tasklist li.today, #tasklist li.past { background-color:#ffffff; border-color:#dedede; } +.task-prio { font-weight:bold; } + +li.task-completed { opacity:1; } + +#footer_content { border-top:1px solid #777777; background:none; } +#footer_content a { text-decoration:none; color:#000000; } + +#tagcloudbtn { display:none; } +.mtt-notes-showhide { display:none; } +#taskview img { display:none; } \ No newline at end of file diff --git a/sources/www/themes/default/style.css b/sources/www/themes/default/style.css new file mode 100644 index 0000000..36d2132 --- /dev/null +++ b/sources/www/themes/default/style.css @@ -0,0 +1,352 @@ +/* + This file is a part of myTinyTodo. + Copyright 2009-2010 Max Pozdeev +*/ + +/* default style */ + +html { height:100%; overflow-y:scroll; } +body { margin:0px; padding:0px; height:100%; min-height:100%; background-color:#fff; font-family:arial; font-size:10pt; } +#wrapper { margin:0px auto; max-width:950px; height:100%; } +#container { height:auto !important;height:100%;min-height:100%; } +#mtt_body { padding:8px; padding-bottom:16px; } + + +td, th, input, textarea, select { font-family:arial; font-size:1em; } +form { display: inline; } +h2,h3 { margin:0; } +h2 { font-size:1.5em; float:left; padding-right:10px; background-color:#ffffff; } +h3 { border-bottom:2px solid #B5D5FF; margin-bottom:10px; padding:6px 0; font-size:1.1em; } +#page_tasks h3 { padding-left:4px; padding-right:4px; } +a { color:#0000ff; cursor:pointer; text-decoration:underline; } + +#space { height:30px; } +#footer { height:30px; margin-top:-30px; } +#footer_content { background-color:#b5d5ff; padding:5px; font-size:0.8em; } +#footer_content a { color:#000000; } + +#bar { border-bottom:1px solid #b5d5ff; padding-bottom:5px; height:15px; } +.bar-menu { float:right; } +.nodecor { text-decoration:none; } +#bar_logout { display:none; } +#bar_auth { display:none; } +#authform { overflow: hidden; z-index:100; background-color:#f9f9f9; border:1px solid #cccccc; padding:5px; width:160px; } +#authform div { padding:2px 0px; } +#authform div.h { font-weight:bold; } +#loading { float:left; padding-top:5px; background-color:#ffffff; display:none; padding-right:6px; width:16px; height:16px; background:url(images/loading1.gif) no-repeat; } + +#msg { float:left; } +#msg .msg-text { padding:1px 4px; font-weight:bold; cursor:pointer; } +#msg .msg-details { padding:1px 4px; background-color:#fff; display:none; max-width:700px; } +#msg.mtt-error .msg-text { background-color:#ff3333; } +#msg.mtt-error .msg-details { border:1px solid #ff3333; } +#msg.mtt-info .msg-text { background-color:#EFC300; } +#msg.mtt-info .msg-details { border:1px solid #EFC300;} + +.mtt-tabs { list-style:none; padding:0; margin:0; } +.mtt-tabs li { margin:1px 3px 0 0; float:left; border-left:1px solid #ededed; background:#fbfbfb url(images/tab_hover.gif) no-repeat top right; } +.mtt-tab a { position:relative; margin:0; font-size:0.9em; font-weight:bold; text-decoration:none; text-align:center; white-space:nowrap; color:#444444; display:block; height:21px; padding:6px 6px 0px 2px; outline:none; vertical-align:top; } +.mtt-tab a span { display:inline-block; min-width:75px; max-width:195px; cursor:pointer; padding:0; overflow:hidden; } +.mtt-tab .list-action { display:none; float:left; position:absolute; top:6px; right:5px; width:15px; height:15px; background:transparent url(images/icons.gif) 0 0 no-repeat; cursor:pointer; } +.mtt-tab .list-action:hover, .mtt-tab .list-action.mtt-menu-button-active { background-position:-16px 0; } +.mtt-tab.mtt-tabs-selected span { margin-right:16px; } +.mtt-tab.mtt-tabs-selected .list-action { display:block; } +.mtt-tab.mtt-tabs-selected { background:#ededed url(images/corner_right.gif) no-repeat top right; border-left:1px solid #ededed; } +.mtt-tabs li:hover a { color: #888888; } +.mtt-tabs.mtt-tabs-only-one li { display:none; } +.mtt-tabs.mtt-tabs-only-one li.mtt-tabs-selected { display:block; } +#mtt_body.readonly li.mtt-tabs-selected span { margin-right:0; } +.mtt-tabs-hidden { display:none; } + +.mtt-tabs-alltasks { margin:1px 3px 0 3px; float:right; border-right:1px solid #ededed; background:#fbfbfb url(images/tab_hover.gif) no-repeat top left; } +.mtt-tabs-alltasks.mtt-tab a { padding:6px 2px 0px 6px; } +.mtt-tabs-alltasks.mtt-tab.mtt-tabs-selected { border-left:none; border-right:1px solid #ededed; background:#ededed url(images/corner_left.gif) no-repeat top left; } + + +#tabs_buttons { + float:right; + padding-top:4px; + padding-bottom:2px; + padding-left:2px; + padding-right:2px; + border:1px solid #ededed; + border-bottom:none; + margin-top:1px; + -moz-border-radius-topright:5px; -webkit-border-top-right-radius:5px; border-top-right-radius:5px; +} + +.mtt-tabs-button { + float:left; + font-size:0.9em; + padding:1px; /* makes button bigger */ + border:1px solid transparent; /* preallocate space for :hover border */ +} + +.mtt-tabs-button span { + display:block; + width:16px; + height:16px; +} + +.mtt-tabs-button:hover, .mtt-tabs-button.mtt-menu-button-active { + border:1px solid #ccc; -moz-border-radius:3px; -webkit-border-radius:3px; border-radius:3px; +} + +.mtt-tabs-add-button { float:left; margin-top:1px; padding:6px 2px 0px 2px; font-size:0.9em; height:21px; border-left:1px solid #ededed; background:#fbfbfb url(images/tab_hover.gif) no-repeat top right; } +.mtt-tabs-add-button:hover { cursor:pointer; } +.mtt-tabs-add-button>span { display:block; width:16px; height:16px; background:url(images/buttons.png) 0 0 no-repeat; } +.mtt-tabs-add-button:hover>span { background-position:-16px 0; } +#mtt_body.readonly .mtt-tabs-add-button { display:none; } + +.mtt-tabs-select-button>span { background:url(images/icons.gif) -64px 0 no-repeat; } +.mtt-tabs-select-button:hover>span, .mtt-tabs-select-button.mtt-menu-button-active>span { background-position:-80px 0; } + + +#mtt_body.no-lists #toolbar > * { visibility:hidden; } +.mtt-htabs { clear:both; padding:8px; border-bottom:2px solid #DEDEDE; background:#ededed; } + +.mtt-img-button { width:16px; height:16px; padding:2px; border:1px solid transparent; display:inline-block; } +.mtt-img-button:hover { border:1px solid #ccc; -moz-border-radius:3px; -webkit-border-radius:3px; border-radius:3px; } +.mtt-img-button span { display:inline-block; width:16px; height:16px; } + +.arrdown { display:inline-block; height:7px; width:9px; background:url(images/arrdown.gif); } +.arrdown2 { display:inline-block; height:7px; width:7px; background:url(images/arrdown2.gif); } + + +/* Quick Task Add */ + +.mtt-taskbox td.mtt-tb-cell { padding:0px; width:450px; } +.mtt-tb-c { position:relative; padding-left:22px; /*input padding+border*/ } +#task { color:#444444; background:#fff; height:1.35em; padding:2px; padding-right:18px; border:1px inset #F0F0F0; width:100%; margin-left:-22px; } +#task_placeholder span { display:none; color:#ccc; position:absolute; left:0; top:0; height:1.35em; line-height:1.35em; padding:3px; /*input top and left padding+border*/ } +#task_placeholder.placeholding span { display:inline-block; } + +.mtt-taskbox-icon { width:16px; height:16px; position:absolute; top:50%; margin-top:-8px; } +.mtt-taskbox-icon.mtt-icon-submittask { background:url(images/mzl.png) 0px -32px no-repeat; right:4px; } + +#newtask_adv span { background:url(images/buttons.png) 0 -48px no-repeat; } +#newtask_adv:hover span { background-position:-16px -48px; } +#mtt_body.show-all-tasks #htab_newtask, #mtt_body.readonly #htab_newtask { display:none; } + + +/* Live Search */ +#htab_search { float:right; } +#search { + color:#444444; background:#fff; height:1.35em; padding:2px 18px; width:100%; margin-left:-38px; /*padding+border*/ + border:1px inset #F0F0F0; -moz-border-radius:10px; -webkit-border-radius:10px; border-radius:10px; +} +#search_close { display:none; } + +.mtt-searchbox td { padding:0px; width:180px; } +.mtt-searchbox-c { position:relative; padding-left:38px; /*input padding+border*/ } +.mtt-searchbox-icon { width:16px; height:16px; position:absolute; top:50%; margin-top:-8px; } + +.mtt-searchbox-icon.mtt-icon-search { background:url(images/mzl.png) 0px -16px no-repeat; left:4px; } +.mtt-searchbox-icon.mtt-icon-cancelsearch { background:url(images/mzl.png) 0px 0px no-repeat; right:4px; } + +#searchbar { font-size:1em; font-weight:normal; display:none; margin-top:5px; } +#searchbarkeyword { font-weight:bold; } + + +/* */ +#mtt_body.no-lists #page_tasks h3 > * { visibility:hidden; } +.mtt-notes-showhide { font-size:0.8em; font-weight:normal; margin-left:2px; margin-right:2px; } +.mtt-notes-showhide a { text-decoration:none; border-bottom:1px dotted; } + +#mtt_filters { font-size:0.8em; font-weight:normal; } +.tag-filter { margin-left:3px; margin-right:3px; } +.tag-filter-exclude { text-decoration:line-through; } +.mtt-filter-header { font-weight:bold; margin-right:.33em; } +.mtt-filter-close { cursor:pointer; position:relative; top:2px; margin-left:3px; display:inline-block; width:10px; height:10px; background:url(images/closetag.gif) 0 0 no-repeat; } + +.task-left { float:left; } +.task-toggle { visibility:hidden; margin-top:2px; cursor:pointer; width:15px; height:15px; float:left; background:url(images/icons.gif) -64px -16px no-repeat; } +li.task-has-note .task-toggle { visibility:visible; } +li.task-expanded .task-toggle { background-position:-80px -16px; } +.task-middle { margin-left:40px; margin-right:20px; } +#tasklist { list-style-type: none; margin: 0; padding: 0;} +#tasklist li { padding:6px 2px 6px 6px; border-bottom:1px solid #DEDEDE; min-height:18px; margin-bottom:1px; background-color:#fff; } +#tasklist li:hover { background-color:#f6f6f6; } +.task-actions { float:right; width:20px; text-align:right; } +.task-date { color:#999999; font-size:0.8em; margin-left:4px; display:none; } +.task-date-completed { color:#999999; display:none; margin-left:5px; } +.show-inline-date .task-date { display:inline; } +.show-inline-date li.task-completed .task-date-completed { display:inline; } +.show-inline-date li.task-completed .task-date { display:none; } +.task-through { overflow:hidden; } +.task-through-right { float:right; } +.task-title a { color:#000000; } +.task-title a:hover { color:#af0000; } +#mtt_body.readonly #tasklist li .task-actions { display:none; } +.task-listname { background-color:#eee; color:#555; padding:0px 3px; } +.task-tags { padding:0px 2px; } +.task-tags .tag { font-size:0.8em; font-weight:bold; color:#333333; text-decoration:underline; } +.task-tags .tag:hover { } +.duedate { color:#333333; padding:0px; padding-left:1px; margin-left:5px; } +li.task-completed .duedate { /*font-size:0.8em;*/ display:none; } +#tasklist li.soon .duedate { color:#008000; } +#tasklist li.today .duedate { color:#FF0000; } +#tasklist li.past .duedate { color:#A52A2A; } +li.task-completed .task-middle { color:#777777;} +li.task-completed .task-through { text-decoration:line-through; } +li.task-completed .task-title a { color:#777777; } +#tasklist li.task-completed { opacity:0.6; filter:alpha(opacity=60); } +#tasklist li.task-completed:hover { opacity:1.0; filter:alpha(opacity=100); } +#tasklist li.not-in-tagpreview { opacity:0.1; filter: alpha(opacity=10); } +#tasklist li.mtt-task-placeholder { + min-height:0px; padding:0px; height:18px; line-height:18px; + background-color:#ddd; border:1px solid #aaa; + -moz-border-radius:5px; -webkit-border-radius:5px; border-radius:5px; +} + +a.taskactionbtn { display:block; float:right; height:15px; width:15px; text-decoration:none; background:url(images/icons.gif) 0 0 no-repeat; display:none; } +li:hover a.taskactionbtn, a.taskactionbtn.mtt-menu-button-active { background-position:-16px 0; display:block;} + +#tasklist.filter-past li, #tasklist.filter-today li, #tasklist.filter-soon li { display:none; } +#tasklist.filter-past li.past, #tasklist.filter-today li.today, #tasklist.filter-soon li.soon { display:block; } +#tasklist.filter-past li.task-completed, #tasklist.filter-today li.task-completed, #tasklist.filter-soon li.task-completed { display:none; } + +.task-note-block { margin-left:2px; color:#777777; background:url(images/page_white_text.png) left 2px no-repeat; padding-left:19px; padding-top:2px; min-height:16px; margin-top:2px; display:none; } +li.task-expanded .task-note-block { display:block; } +li.task-completed .task-note-block .task-note { text-decoration:line-through; } +.task-note-area { display:none; margin-bottom:5px; } +.task-note-area textarea { color:#999999; width:100%; display:block; height:65px; } +.task-note-actions { font-size:0.8em; } +.hidden { display:none; } +.invisible { visibility:hidden; } +.in500 { width:500px; color:#444444; } +.in100 { width:100px; color:#444444; } +.task-note span a { color:#777777; } +.task-note span a:hover { color:#af0000; } + +.task-prio { padding-left:2px; padding-right:2px; margin-left:0px; margin-right:5px; cursor:default; } +.prio-neg { background-color:#3377ff; color:#ffffff; } +.prio-pos { background-color:#ff3333; color:#ffffff; } +.prio-pos-1 { background-color:#ff7700; color:#ffffff; } +.prio-zero { /*background-color:#dedede;*/ } +.task-prio.prio-zero { display:none; } + +.form-row { margin-top:8px; } +.form-row .h { font-weight:bold; color:#333333; } +.form-row-short-end { clear:both; } +#page_taskedit .form-row .in500 { width:99%; } +#page_taskedit .form-row textarea.in500 { height:200px; /*resize:none;*/ } +#page_taskedit .form-row-short { float:left; margin-right:12px; } +#page_taskedit .form-bottom-buttons { text-align:center; } +#alltags .tag { font-weight:bold; color:#333333; } +#alltags .tag:hover { background-color:#999988; color:white; } +.alltags-cell { width:1%; white-space:nowrap; padding-left:5px; } +#page_taskedit.mtt-inadd .mtt-inedit { display:none; } +#page_taskedit.mtt-inedit .mtt-inadd { display:none; } +#taskedit-date { font-size:1em; font-weight:normal; display:inline; color:#777; margin-left:8px; } + +a.mtt-back-button { font-size:0.8em; } + +/* autocomplete */ +.ac_results { padding:0px; border:1px solid #cccccc; background-color:#f9f9f9; overflow:hidden; z-index:99999; -moz-box-shadow:1px 2px 5px rgba(0,0,0,0.5); -webkit-box-shadow:1px 2px 5px rgba(0,0,0,0.5); } +.ac_results ul { width: 100%; list-style-position: outside; list-style: none; padding: 0; margin: 0; } +.ac_results li { margin: 0px; padding: 2px 5px; cursor: default; display: block; line-height: 16px; overflow: hidden; } +.ac_over { background-color:#316AC5; color:white; } + +#priopopup { overflow: hidden; z-index:100; background-color:#f9f9f9; border:1px solid #cccccc; padding:5px; } +#priopopup span { cursor:pointer; border:1px solid #f9f9f9; } +#priopopup .prio-zero:hover { border-color:#dedede; } +#priopopup .prio-neg:hover { border-color:#3377ff; } +#priopopup .prio-pos:hover { border-color:#ff3333; } +#priopopup .prio-pos-1:hover { border-color:#ff7700; } + +#tagcloudbtn { margin-right:2px; font-size:0.8em; font-weight:normal; padding:2px; float:right; } +#mtt_body.show-all-tasks #tagcloudbtn { display:none; } +#tagcloudload { display:none; height:24px; background:url(images/loading1_24.gif) center no-repeat; } +#tagcloud { + overflow: hidden; z-index:100; background-color:#f9f9f9; border:1px solid #cccccc; padding:5px; + width:100%; max-width:450px; margin:0px 7px 7px 7px; text-align:center; + -moz-box-shadow:1px 2px 5px rgba(0,0,0,0.5); -webkit-box-shadow:1px 2px 5px rgba(0,0,0,0.5); +} +#tagcloud .tag { margin:1px 0px; padding:2px; line-height:140%; color:black; } +#tagcloud .tag:hover { background-color:#999988; color:white; } +#tagcloud .w0 { font-size:80%; } +#tagcloud .w1 { font-size:90%; } +#tagcloud .w2 { font-size:100%; } +#tagcloud .w3 { font-size:110%; } +#tagcloud .w4 { font-size:120%; } +#tagcloud .w5 { font-size:130%; } +#tagcloud .w6 { font-size:140%; } +#tagcloud .w7 { font-size:150%; } +#tagcloud .w8 { font-size:160%; } +#tagcloud .w9 { font-size:170%; } + +#tagcloudcancel { float:right; } +#tagcloudcancel span { background:url(images/buttons.png) 0 -32px no-repeat; } +#tagcloudcancel span:hover { background-position:-16px -32px; } + +#taskview { padding:2px; } + +.ui-datepicker { width:190px; z-index:202; border: 1px solid #cccccc; background: #ffffff; display:none; padding:2px; + -moz-box-shadow:1px 2px 5px rgba(0,0,0,0.5); -webkit-box-shadow:1px 2px 5px rgba(0,0,0,0.5); box-shadow:1px 2px 5px rgba(0,0,0,0.5); + -moz-border-radius:5px; -webkit-border-radius:5px; border-radius:5px; +} +.ui-datepicker-trigger { cursor:pointer; vertical-align:text-bottom; margin-left:1px; } +.ui-datepicker-calendar { width:100%; border-collapse:collapse; } +.ui-datepicker-calendar thead th { text-align:center; padding:0px; font-size:0.9em; } +.ui-datepicker-calendar tbody td { text-align:right; padding:1px; } +.ui-datepicker-calendar td a { display:block; text-decoration:none; color:#444444; border:1px solid #cccccc; background-color:#f9f9f9; color:#111; padding:1px; } +.ui-datepicker-calendar td.ui-datepicker-current-day a { background-color:#EAF5FF; color:#222222; border-color:#5980FF; } +.ui-datepicker-calendar td.ui-datepicker-today a { color:#fff; background-color:#ccc; } +.ui-datepicker-calendar td a:hover { border-color:#5980FF; } +.ui-datepicker-header { padding:3px 0px; } +.ui-datepicker-prev { position:absolute; left:2px; height:20px; text-decoration:none; } +.ui-datepicker-next { position:absolute; right:2px; height:20px; text-decoration:none; } +.ui-datepicker-title { text-align:center; line-height:20px; } +.ui-icon { width:16px; height:16px; text-indent:-99999px; overflow:hidden; } +.ui-datepicker .ui-icon-circle-triangle-w { display:block; position:absolute; top:50%; margin-top:-8px; left:50%; background:url(images/icons.gif) -48px -16px no-repeat; } +.ui-datepicker .ui-icon-circle-triangle-e { display:block; position:absolute; top:50%; margin-top:-8px; right:50%; background:url(images/icons.gif) -32px -16px no-repeat; } + +.mtt-menu-button { + -moz-user-select:none; -webkit-user-select: none; + cursor:pointer; + border:1px solid transparent; +} +.mtt-menu-button:hover, .mtt-menu-button.mtt-menu-button-active { + border:1px solid #ccc; -moz-border-radius:3px; -webkit-border-radius:3px; border-radius:3px; +} + +.mtt-menu-container { + overflow:hidden; z-index:100; + background-color:#f9f9f9; border:1px solid #cccccc; padding:2px 0px; + -moz-box-shadow:1px 2px 5px rgba(0,0,0,0.5); -webkit-box-shadow:1px 2px 5px rgba(0,0,0,0.5); box-shadow:1px 2px 5px rgba(0,0,0,0.5); + -moz-border-radius:5px; -webkit-border-radius:5px; border-radius:5px; + margin:0px 7px 7px 0px; /* for shadows */ +} +.mtt-menu-container ul { list-style: none; padding:0; margin:0; } +.mtt-menu-container li { margin:1px 0px; cursor:default; color:#000; white-space:nowrap; padding:0.15em 0px; padding-left:24px; padding-right:18px; position:relative; } +.mtt-menu-container li:hover, .mtt-menu-container li.mtt-menu-item-active { + background-color:#316AC5; + color:white; + background:-moz-linear-gradient(#5373fc, #3157f4); + background:-webkit-gradient(linear, left top, left bottom, from(#5373fc), to(#3157f4)); +} +.mtt-menu-container li.mtt-item-disabled, .mtt-menu-container li.mtt-item-disabled a { color:#ACA899; } +.mtt-menu-container a { display:block; cursor:default; text-decoration:none; outline:none; color:#000; } +.mtt-menu-container li:hover a { color:white; } +.mtt-menu-container li.mtt-menu-delimiter { height:0px; line-height:0; border-bottom:1px solid #cccccc; margin:2px -1px; padding:0px; font-size:0px; } +.mtt-menu-container .menu-icon { width:16px; height:16px; position:absolute; left:4px; top:50%; margin-top:-8px; } +li.mtt-item-checked .menu-icon { background:url(images/icons.gif) -16px -16px; } +li.mtt-menu-indicator .submenu-icon { + position:absolute; right:2px; top:50%; margin-top:-8px; + width:16px; height:16px; background:url(images/icons.gif) -32px -16px no-repeat; +} +li.mtt-item-hidden { display:none; } + +#slmenucontainer li.mtt-list-hidden a { font-style:italic; } +#cmenulistscontainer li.mtt-list-hidden { font-style:italic; } + +#btnRssFeed .menu-icon { background:url(images/buttons.png) -16px -64px no-repeat; } +#btnRssFeed.mtt-item-disabled .menu-icon { background:url(images/buttons.png) 0px -64px no-repeat; } + +.mtt-settings-table { width:100%; border-collapse:collapse; } +.mtt-settings-table th, .mtt-settings-table td { border-bottom:1px solid #dedede; padding:8px; vertical-align:top; } +.mtt-settings-table .form-buttons { border-bottom:none; text-align:center; } +.mtt-settings-table th { text-align:left; width:210px; padding-left:8px; } +.mtt-settings-table .descr { font-size:0.8em; font-weight:normal; color:#222; } +.mtt-settings-table .in350 { min-width:350px; } diff --git a/sources/www/themes/default/style_rtl.css b/sources/www/themes/default/style_rtl.css new file mode 100644 index 0000000..df489f2 --- /dev/null +++ b/sources/www/themes/default/style_rtl.css @@ -0,0 +1,33 @@ +body { direction:rtl; } +h2 { float:right; padding-left:10px; padding-right:0px; } +.bar-menu { float:left; } +#loading { float:right; } +#lists .mtt-tabs { float:right; } +.mtt-tabs li { float:right; margin:1px 0 0 3px; border-left:none; border-right:1px solid #ededed; background:#fbfbfb url(images/tab_hover.gif) no-repeat top left; } +.mtt-tabs li.mtt-tabs-selected { border-left:none; border-right:1px solid #ededed; background:#ededed url(images/corner_left.gif) no-repeat top left; } + +#tabs_buttons { float:left; } +.mtt-tabs-button { float:right; } +#tagcloudbtn { float:left; } + +#htab_search { float:left; } +#task { padding: 2px 2px 2px 18px; } +#task_placeholder span { right:0px; left:auto; } +.mtt-taskbox-icon.mtt-icon-submittask { left:4px; right:auto; } +.mtt-searchbox-icon.mtt-icon-search { right:4px; left:auto; } +.mtt-searchbox-icon.mtt-icon-cancelsearch { left:4px; right:auto; } + +.task-actions { float:left; text-align:left; width:15px; } +.task-left { float:right; } +.task-toggle { float:right; } +.task-middle { margin-right:40px; margin-left:25px; } +.task-date { margin-right:4px; } +.duedate { float:left; margin-left:0; margin-right:5px; } +.duedate-arrow { display:none; } +.duedate:before { content:'\2190'; } +.task-through-right { float:left; } + +#taskedit-date { float:left; } +#page_taskedit .form-row-short { float:right; margin-left:12px; margin-right:0; } +.task-prio { float:right; margin-left:4px; margin-right:0; } +.alltags-cell { padding-left:0; padding-right:5px; } \ No newline at end of file diff --git a/sources/www/themes/index.html b/sources/www/themes/index.html new file mode 100644 index 0000000..fe49470 --- /dev/null +++ b/sources/www/themes/index.html @@ -0,0 +1 @@ +somewhere \ No newline at end of file diff --git a/sources/www/tmp/.htaccess b/sources/www/tmp/.htaccess new file mode 100644 index 0000000..3418e55 --- /dev/null +++ b/sources/www/tmp/.htaccess @@ -0,0 +1 @@ +deny from all \ No newline at end of file